Oregon State University|blogs.oregonstate.edu

Mana Burn in the Real World

  February 24th, 2023

In keeping with the theme of Trading Card Game based blog post intro’s, are you familiar with Mana Burn? I’ve heard that this rule was actually removed form the official rules for Magic: The Gathering, but there used to be a rule that a player took damage equal to the number of unspent mana left in their mana pool at the end of their turn. For you non-magic players, the basic idea behind mana is: In magic you play “land” cards, during your turn you can “tap” (activate) land cards to produce mana (each land generally can only produce a single mana per turn, and you gather more lands on your board as the game progresses). Spells, creatures and basically everything in the game costs mana to use. Mana burn didn’t affect the game much, because for the most part you tap lands when you are ready to use the mana, so you never unnecessarily tap extra land. It was a rule that prevented certain obscure strategies and most commonly would catch newer players who would just tap all their land at the start of a turn and then try and use the mana only to realize they couldn’t use it all. So what does this have to do with coding, the TCG Maker Capstone project, or anything related to the list of acceptable topics for our mandatory blog posts? Mana Burn is a metaphor for the subtle art of dealing with discrepancy between task allocation management and the reality of what happens when you try to do the work.

I’ve recently hit my 9 month mark at my first company as a Software Engineer (really I started as a Software intern and then got hired on full time). People warned me about it, but I still didn’t quite grasp just how little of the time and energy of a developer/engineer is spent doing everything but actually coding. A huge part of the job is planning work, refining stories, pointing stories, writing documentation, outlining solutions and the list goes on. Basically, lots and lots of trying to guess and predict what a software implementation will require. If development were a magic game it is as if you have to tap land before looking at your hand. Sometimes you over-estimate a task, sometimes under. Sometimes the way you thought you could do something proves impractical and you have to circle back and re-evaluate the plan after starting down a given implementation path. This is okay. It has been hard for me to deal with both the moments in which I realize I tapped too much land (made a task out to be more complex than it turned out to be) and in which I didn’t tap enough (and found my managers and peers waiting anxiously for me to finish something that I thought would be simple and ended up taking far longer than expected).

So whether it is mana burn or mana shortage, I have learned one thing. It is okay. Everyone has been there. It’s the same in our capstone project. One person’s designated task, which in the planning phase seemed an equal piece of the pie to everyone else’s, has proved far more complex and time consuming, while the pieces that myself and others took on were able to be completed in the target timeline. This is okay. None of us feel anything but a desire to support the person who is behind on their target timeline. And ultimately, there is plenty for everyone to do, and we are going to pull it off. The only person truly distressed by the delay is the person working the task. And that’s honestly how it is (for the most part) in a professional setting as well. I mean, of course if you really mess up people get frustrated. But story pointing is always a best guest. And most of the time, honestly saying “I over/under estimated this task” is all it takes to get the full support of your team and manager in either finding the next thing, or re-allocating resources to accommodate the delay.

The round about point is this: Gracefully dealing with divergence from expected work-plans is an often under-appreciated “soft-skill”. The biggest issue that arises from tapping the wrong amount of land for a project is when a developer gets stressed and starts communicating poorly or, even worse, lashing out in frustration. Maintaining a level head and openly admitting the discrepancy not only helps you avoid unnecessary stress, but it is so appreciated by team-mates. I noticed that when I tried to deal with it all internally, that is when I got mana burned. When I talked openly, the new rules applied and the excess or shortage of mana was gracefully dealt with, and often unexpected learning opportunities emerged. So don’t worry too much about the “planning vs reality” divide. It is part of the job. You have to map out expectation in order to task out the work, but everyone knows that things don’t always go to plan. Mana Burn is not a thing anymore (for the most part), but watch out when you’re getting started, because mana burn is still a classic pitfall for new players :D.



It ain’t called Magic the gathering because you do it alone…

  February 10th, 2023

Okay, so in my ongoing efforts to keep my post title’s Trading Card Game themed, this may be stretch. But, I think it’s better than my original idea: “The Heart of the Cards is Teamwork”. Between the two, you can guess that today we are voyaging out of high-brow technical discussions of frameworks and system designs and moving into the often much harder realm of “Soft Skills”. Yep, today we are talking about what it takes to work on a team.

In the ongoing saga of Making the Trading Card Game Maker we are making progress and also running into the lovely cross-section of coordination that is part of having a team built of devs spanning time zones, life commitments and experience. Let me start out by saying, it is all going surprisingly well, but I wanted to talk about a few categories of building positive team environment inspired by this work. I want to add that these themes are a huge part of my experience as a professional software engineer, and I don’t think importance of positive team dynamics can ever be understated.

Division of Labor:

This is a key part to the development process, but is often fraught with complicating factors in terms of team dynamics. For instance, on a team of devs with a list of tasks divided up, do we prioritize giving tasks to folks who have something to learn from doing it, or who will finish it the quickest. What if multiple people want to work on the same thing? This is one of those questions that will always have a unique answer for the given collaboration. Are we working to a deadline, or with a looser time frame. Is this a one and done project, or can we say “you get first pick this sprint, and then you get first pick next sprint”. On our team it was a simple as coming up with the tasks and people all seemed interested in taking different ones, so we divided it up pretty easily. But then what happens as the process progresses?

Output Result:

This is the big inspiration of my post. How does a team handle the difference in time it takes to accomplish different tasks. For instance, if one person takes on a task using an entirely new technology with a steep learning curve complex technical requirements, while another takes on one with a familiar technology and relatively standard technical requirements. This is exactly what has happened on our team. Where one team member is bogged down in the learning process feeling he has fallen behind, another team member has finished his designated tasks and the third is on-pace with the plan and having manageable time completing the designated tasks. The simplest solution to this is pair programming, right? Just have the person who has completed their designated work hop in with the person who is feeling behind. This is a good approach in some ways, but also leads to lots of complications. Sometimes bringing in another person on a task actually slows it down, or can be disillusioning to the person who has been plugging away. This brings me to my final pitch:

Pair Programming: The Consultant Method:

I have been involved with a number of situations where I plug-in with or have someone plug-in with me on a in-flight project. There are many approaches to “Pair Programming”, but to me the approach which works best is what I call “The Consultant Method”. Having someone jump in with you and try and take on an even share of the work is rough and often leads to more overhead. What I recommend is that the person joining the in flight project treat themselves more as a consultant and extra hands for side-tasks. If they jump in and demand to be brought up to speed and fully plugged in this slows things down, but if they say, “Why don’t you share screen with me and show me what you’re working on” then they become more of a rubber duck than another chef in the kitchen (If you’ve never heard of Rubber Ducking I recommend looking up the term, it is a great tool for programmers). Your job as the Consultant is to ask good questions, notice things that a person whose been staring at the same code for weeks might miss, and complete some of side tasks they may have let fall to the wayside. Offer to write up documentation for them or research questions they had which we outstanding. I recently had someone at work “pair program” with me, hopping in halfway, and they noticed there was one part of the project which required communicating with other teams at the company. They happened to have worked with the PM for that other team and offered to initiate the discussion. They took point on this inter-team discussion piece of the progress so I could stay heads-down on my primary sub-task. And it worked GREAT!

Conclusion:

Really, the point of all this is to say, Teamwork is about listening. It’s about noticing what’s missing and filling that niche. Trying to do the same thing your teammate is doing does not reduce the time it takes to get it done. It complicates thing. Working together is always about becoming the missing piece. That’s what my team is doing great so far, and that’s what I think we could all work on.



Node.js I Choose You!

  January 27th, 2023

The Trading Card Game Maker Creation is underway! And to make our maker we have to decide what languages and frameworks we will be making the calls to our maker to make the cards to make the decks to make the games to play and build in the TCG Maker (I promised run-on making of the maker statements in my last post, so you were warned!). One of my major tasks this sprint has been provisioning and standing up the skeleton of our Backend API. In the discussions with our team around what languages to use for both Frontend and Backend, as well as what sort of databases and frameworks to employ, I got to thinking about all my experience working with various technologies for building RESTful API’s. Spoiler alert, we chose to use React for our frontend, and after some debate settled on Node.js and Express for building the backend API (hosting on Google Cloud and using Firebase for our Database). I wanted to take this blog post to wax poetical on this decision and other Backend API architectures I have worked with. Before I can dive into that, let me offer a brief summary of REST API’s and my experience building them.

First and foremost – I love a good REST API. I like the idea of API calls grounded in the “Nouns” of our craft rather than the verbs. So quick breakdown: an API (Application Programming Interface) is any of a multitude of tools for communicating between pieces of software. An API is how one program asks another to do something. In our project the User Interface will need an “API” to ask the database to store new card games, to generate the information needed to play the games and countless other little interactions between the information and functionality and the actual user interface. REST is an approach to building API’s around a language of HTTP requests that use (and this is of course a simplification and summary skipping many important caveats) a short list of Actions combined with a target Entity. The core set of actions are GET, POST, PUT, PATCH and DELETE. Combining these simple actions with a complex matrix of Entities allows us to do an incredible amount of stuff. The second part of a RESTful HTTP call is the address the verb targets, which is always something like “/decks” or “/users” and never* “/save_a_card” or “/generate_opponent”. If we want to save a card, we can POST to “/games/[name_of_our_game]/cards” and magically our actions mesh seemlessly into our data models. There is so much more that could be said about this topic, but let’s keep moving toward the great tech stack debates.

The final thing I’ll say by way of introduction is that I am more than a novice but by no means an advanced student of the API arts. I’ve taken OSU’s course on cloud based API’s where I built REST API’s with both Node/Javascript/Express systems and Flask/Python systems, and used both of these in other course work and pet projects. I work for a company that sells cars online and I have built backend API’s for them as well, all using Kotlin/Spring Boot though some in the CoRoutine style and others in the more classic Reactive approach. At the end of the day, I’ve put together programs that receive HTTP Requests in a variety of ways. I’ve also built these systems using, among others, MongoDB, Datastore, Firebase, MySQL, and PostgreSQL. Here’s my thoughts:

For enterprise level API’s, there is something to be said for the legendary through-put of Reactive Spring based systems (usually written in Java, or its evolved form, Kotlin), but at the end of the day, when writing an API you want to be able to define functionality for endpoints. All the extra bells and whistles, not to mention the nested function chain headaches of Reactive frameworks obscures the simple, beautiful core of what we do with RESTful API’s. CoRoutines is to Reactor what Async/Await is to Promises in Javascript. It solves some of the problem, but it all comes short of the simple beauty of Flask. I love Flask. Let’s just show the simplicity telescoping of say, writing a GET all games endpoint in each of the systems I’ve listed.

  1. (most complicated) Kotlin/Spring Boot with WebFlux/Reactive would look like two files at a minimum. One containing a function defining routers like (if you want to imagine this in Java just add 4 extra words or symbols to each line in your mind’s eye):

“`@Bean

fun tcgRoutes(: RouterFunction<ServerREsponse = router {

GET(“/games”, tcgHandler::getGames)

}

And then somewhere else a function that has to deserialize ServerRequest objects and serialize into ServerResponse objects and so on. Sure, it runs fast, but this is json bodies containing amounts of data orders of magnitude smaller than the simplest real-time computer game. We don’t need that efficiency. We need code that is easy to read.

2. (medium complicated) In Express/Node we get a simpler sort of architecture. We have to define a bunch of “requires” objects and whatnot at the top, tell our app to start listening on a port with a function call but at least we can right queries of our database inline right bellow the route. It looks something like:

app.get(“/games”, (req, res) => {

let dbQuery = Firestore.collection(“games”);

let allGames = {};

let queryResult = await dbQuery.get()

queryResult.forEach(element => allGames[element.id] = element.data())

res.json(allGames);

};

Cleaner, leaner, and very digestable. This is the system we chose, and we chose it partially because it has the simplicity and readability one would like, and also because as a team our composite experience in Flask vs Express was strongly leaning toward Express.

3. (simple beauty) But just for those of you who haven’t given up on this blog post yet, what would the same code be in Flask? Let me show you:

@app.route(‘/games’, methods=[‘GET’])
def allGamesRoute():
allGames = Firestore.get(‘games’)
return json.dumps(allGames), 200

And that’s it. Why do I like this so much, in many ways it is not that different from express. But, it does provide a simple way to group your processing for a given endpoint with the methods array. That could be methods=[‘GET’,’POST’] and then our allGamesRoute function could have a simple conditional (programming 101 level stuff) for the different Verbs. No need for async/await gymnastics and best of all, you just return the body of your response as a classic return statement. To put the cherry on top you can return a tuple with your response code as well, making it super simple to have natural feeling code with simple linear conditionals determining whether to throw a 400 or return some info and a 200. In the end, I suspect Flask is the least “effecient” in terms of cpu usage, with minimal use of threading potential and whatnot. But for writing a REST API, that beautiful system so simple in its building blocks and complex in its possibilities, it allows for easy to read and easy to write implementations. I think Express offers a fine runner up, but outside the benefit of consistent tech-stacks (since we use react for the frontend it’s nice to have a JS/Express based BE as well) and familiarity to the team at large, I think Flask would have been a great option as well.

PS. A brief statement about databases. I love them, and formal Schemas with well though out architectures are lovely. That’s SQL. But when it comes to Agile development and ever changing projects NoSQL DB’s are the way to go. Firebase, Datastore, MongoDB…. doesn’t really matter which you use, they are all optimized at this point. But the freedom of these systems where additional columns can be incorporated without having to re-provision the whole database really lend themselves to dynamic development process. Fini.



It’s time to DUEL!

  January 12th, 2023

That’s right folks, I have officially joined the Online Trading Card Game Maker Capstone Project! What does this mean for you, mystery person reading this blog (aka fellow student and/or grader of this assignment). It means you can burn your Magic Cards and give your Pokemon cards away to the neighbor kids. You can stop wasting all your time pursuing the Gwent side-quests in Witcher, quit considering to buy that fifty-dollar Yu-Gi-Oh! trading card game for Switch, and stop getting your butt kicked by pay-to-win gamers on Hearthstone. It’s time to stop playing these corporate card games and start making and playing free, open-source, and paperless TCG’s!

To kick-off this new blog dedicated to chronicling the epic journey of our intrepid Trading Card Game Maker makers (I’m gonna get a lot of mileage out of the meta-jokes around creating a system for creating a system for creating cards used to create decks to create…. and so on…..), I wanted to take a few paragraphs of your time to talk about why this initiative is a cool idea. There are two perspectives to look at for this project: the User’s experience and the Developer’s endeavor. Before our team of developers embarks on the mission, I’d like to take this moment to imagine what this could be, both in terms of what we create and how we create it.

The USERS!

Ah, to code perchance to dream. If you are like me, then you’ve played your fair share of trading card games. But have you made one? I’ve tried before, but dang is it a lot of work! The part that I love about trying to invent a game is coming up with the rules, the subtle interactions and the epic cards. I’m not a great visual artist myself, but I always dream of being able to get my visual-arts-gifted friends to draw the dragons and aliens of the fantasy battlegrounds I want to create. This project would streamline the process, enabling a simple interface. The game creator menu could offer a card design area, where you set the features of the card (its cost, effect, type, stats, etc). The card design area would allow loading images for the card art, and placing functionality text as well as personality text.

There would also need to be an interface for defining the mechanics of play. Maybe there are some pre-made default templates for building your ruleset (like a Magic-like template that defaults to turn-based play, life totals for players and basic phases to turns). There can also be a more “build from scratch” system where you specify every detail, maybe in your TCG there aren’t turns. Maybe action opportunities are triggered by events and cards rather than turns and phases. Furthermore, you could set the mechanism for obtaining cards, and deck building. Is your game one where every card is available to all players? Is there some collecting dynamic to consider? What are the rules around building decks?

Finally, and most importantly, an interface for playing the games you create! Imagine being able to define the rules, craft the cards, and then click the play button. Does the system provide AI opponents or is it strictly PvP? Maybe you designed a Slay the Spire style PvE TCG! The possibilities are endless, and we probably want to provide an interface for customizing the gameplay in addition to an interface for engaging in play. All of the above brings us to the primary topic of this blog: developing the software!

The DEVELOPERS:

We haven’t spoken a word to eachother yet, so obviously this is all purely speculative, but what might the design and development of this project be like? It seems inevitable that we will want a GUI frontend of some sort, will it be browser based or a free-standing app? We will need complex databases too, that store a variety of entities, from rulesets and customization to card design and peoples’ decks and collections. Will we use SQL style databases, or the wild west of noSQL databases, or even just text files of csv masquerading as databases. How will we host the GUI and the backend? Will they be monolithic and fully integrated or built on a microservice architecture with RESTful calls to an API from an indepent UI?

Will we make a web-based app dependent on a cloud-based server, or perhaps we make the entire software downloadable, and allow users to host instances of this software locally or through their own servers. Are we building a highly adaptable, customizable piece of software that we we let others customize and adapt as they please, or do we build something curated and controlled by our team so that its features and functionality remain streamlined? Do we run the whole project as Free/Libre Open Source Software or do we keep it as our perfect little pet project, safe from the contributions of the wider community?

If you want to know the answer to these questions, like I do, you will have to stay tuned for the posts to come on Stew’s CS Blog! Now officially dedicated to documenting the story of creating an Online Trading Card Game Creator.



Hello world!

  January 9th, 2023

Welcome to blogs.oregonstate.edu. This is your first post. Edit or delete it, then start blogging!