I just wanted to do one little thing

My current project is a company site revamp. Some parts of our site would simply be the old ASP.Net WebForms, tidied up and reskinned.

Some will be more modern — using a React framework and microservices. This is terribly fun, but not 100% greenfield work. We need to stay compatible with the old site, and, in the interest of maintenance, share logic instead of replicating it.

Purportedly, my goal was to integrate an “Add to Cart” feature on a component. No big deal. I’ve been at the company for five years, we’ve had the same basic control, and I’d walked that code a few times. Only… as it turns out…

… our existing Add to Cart logic started in a separate control (suitable), but most of it, including business rules, lived in massive series of methods in a shared BasePage (ASP.Net WebForms.)

I needed to use this in an new, RESTful microservice (WebAPI 2.0). I discarded the idea of trying to force inhertance there (Though it’s possible. MVC has shared ancestor classes. Possible but painful.) That left one of the following:

  • Instantiating the BasePage class from my API classand then using it
  • Copying the logic (shudder)
  • Or finding an appropriate place to move it where both could access it

By the way, our codebase is what’s most politely called mature. Possibly also vast.

I understand the expediency of copy/paste code, especially in a large, old, OO codebase where troubleshooting side effects is cumbersome. I also LOATHE repetition. I would not be making another copy of the same logic.

Working with an instantiated instanced of the class is ok… but also made for some troubleshooting obnoxiousness. Also, that’s a lot of baggage to saddle a little service with.

Remember, all of this is so that I can update my front end code, to have a JSX component something like this:

import React from 'react'; 
import {connect} from 'react-redux';
import PropTypes from 'prop-types';
import {addToCart} from '../cart/asyncActions';

const ProductTile= () => {
  return (
    <div>Fantastic product</div>
    <button type="button" 
        className="btn btn-primary"
        onClick={()=>addToCart(this.props.itemId)}
  )
};

ProductTile.propTypes = {
  addToCart: PropTypes.func.isRequired,
  itemId: PropTypes.string.isRequired
};
const mapDispatch = (dispatch) => {
  return {  
    addToCart: dispatch(addToCart(itemId)
  };
};

export default connect(null, mapDispatch)(MyComponent);

So I neded to move as much of the logic as I could, but efficiently. The original location with my logic ultimately referred to some older libraries we had written in Visual Basic.

The hardest part of my little microservice to be was deciding where to relocate the code, and how much of it I had time to relocate. There was some WebDorms specific show/hide stuff, even one layer deeper than the acx control itself. After the decisions, the move–even writing in VisualBasic– went surprisingly quickly. I maintained the existing method signatures and locations for the current store — just parked the bulk of the work in a deeper layer, to which that class already had a reference. My relocated code worked for our current WebForms store.

Writing the PATCH api call–typos and all — was trivial since I the only real “new” stuff was 10 lines of code, including exception handling, and it integrated seamlessly with our existing carts, session tracking, etc.

My new microservice implementation and its section of the redux store could be improved, but I set that one aside feeling pretty ok.


Comments

Leave a Reply

Your email address will not be published. Required fields are marked *