Aspect Oriented Programming, Steemit API Example

in #utopian-io6 years ago (edited)

Motivation

Aspect Oriented Programming, or AOP for short, is a paradigm aimed at separating so called cross-cutting concerns in our software. You can take an in depth look at what this paradigm is all about, in my post here, https://steemit.com/steemstem/@prometheus21/introduction-to-aspect-oriented-programming, where I have explained this concept. In this tutorial, my aim is to provide a somewhat realistic scenario for AOP use, more so than you would find in a hello world you would find in most documentations. I wanted to get started in experimenting with the steemit API, and I wanted to do an AOP tutorial after my introduction post on the matter, so what better way than to solve two problems in with one solution! If you want to skip right ahead to the end, here is the finished project: Code

What will I learn

  • Connect to the steemit API
  • See who upvoted you
  • Add additional behavior to our code, through the usage of a mechanism called advice

Requirements

  • Basic JavaScript knowledge
  • A plain text editor, I use Atom
  • I would highly recommend reading my AOP post, I will not go on explaining AOP concepts/terminology in this tutorial
  • Node Installed in your machine

Difficulty

  • Basic

So, what does my project actually do?

My script connects to the steemit api, retrieves the account history (number of transactions are also specified ) for an account of your choice. Than, it parses these transactions, extracting the names of those who upvoted you. Every time a new name is found, another method is called, a stub method, wrapped by a JavaScript object, which simply writes the name of the person found to the console. Than, I define an 'advice', in which, I will add additional behavior that is executed before and after the stub method I previously mentioned. In order to keep things simple, this additional behavior is just writing some text to the console, but it can be retooled to write logs to a file for example.

Step 1 - Setting up our workspace

  • Install NodeJs for your platform. You can fetch the latest here
  • Git clone or directly download the code.
  • in the folder where the project is copied, open a command prompt, or a terminal and run npm install
  • run node steem_aspect.js and you will see a list of names and some text, which I will explain

Step2 - Setting up parameters

Firstly, let's import the necessary libraries for our project, the steem API library and the aspects library:

var steem = require('steem');
const around = require('aspectjs').around;

As far as constants go, we specify the number of transactions we want the API to fetch and the targeted account. The default values I have set up are 15 and the target account is mine 😃

// tell the api how many tranzactions you want fetched
const NUMBER_OF_TRANZACTIONS = 15;
// write your account name, or any other account here :)
const NAME = 'prometheus21';

Step3 - API invocation

In our api object, we add a function, getUpvotes, that fetches from the API the last n tranzactions, where n is our NUMBER_OF_TRANZACTIONS constant we have defined. Here is the code for that:

var api = {
  getUpvotes : function() {
    steem.api.getAccountHistory(NAME, 99999999, NUMBER_OF_TRANZACTIONS, function(err, accountHistory) {
      if (err) throw err
      for (var i=0; i < accountHistory.length; i++) {
        var name = process_tranzaction(accountHistory[i]);
        if (name) {
          upvoteObject.add(name)
        }
      }
    });
  },
}

We invoke our API using the constants defined, get an array of transactions in the accountHistory variable. We than process each transaction in a for loop.
We use an auxiliary function, process_tranzaction, to parse the each transaction, which is simply a JSON object and extract the account that upvoted you. You can do console.log(accountHistory[i]) to see how a transaction looks like.
2018-01-28.png

Seeing the data, helps us build the auxiliary function I was mentioning, process_tranzaction. Here we check if the transaction is a voting transactions and return the name of the person who upvoted, if that person was not the target account.

Step4 - Stub method to print out names

Every time we find a name, we call upvoteObject.add(name). Now, this is a trivial method, a stub, that only prints out the name. However, we can imagine other logic being integrated there, for example upvoting a post for that name, or following that account, or any other use case one is interested in. Here is the code for the stub:

var upvoteObject = {
  add: function(supporter){
      console.log('I have an upvote by ' + supporter)
  },
};

Step5 - Adding some advice

For our final part, we shall use the aspectjs to override the call our upvoteObject makes to add. We insert our code before and after the function call. In this case the custom code inserted will be just some console logs.

var advice = {
   override: function(invocation) {
       console.log('Hey, I can do something cool before I find a new upvote')
       invocation.proceed();
       console.log('Hey, I can again do something cool, after I have found the upvote')
       console.log("************")
   }
};

We add our advice to the upvoteObject like this:
around(upvoteObject, "add").add(advice, "override");

With this line, we basically add some extra functionality to our add function, without modifying our add function, which is crucial when we want to separate concerns in our software.

Conclusion

First of all, I want to post the full code again, if you skipped to this part of the post : Code. As this is my first tutorial, feedback would be much appreciated.



Posted on Utopian.io - Rewarding Open Source Contributors

Sort:  

Thank you for the contribution. It has been approved.

You can contact us on Discord.
[utopian-moderator]

Hey @prometheus21 I am @utopian-io. I have just upvoted you!

Achievements

  • You have less than 500 followers. Just gave you a gift to help you succeed!
  • You are generating more rewards than average for this category. Super!;)
  • This is your first accepted contribution here in Utopian. Welcome!

Suggestions

  • Contribute more often to get higher and higher rewards. I wish to see you often!
  • Work on your followers to increase the votes/rewards. I follow what humans do and my vote is mainly based on that. Good luck!

Get Noticed!

  • Did you know project owners can manually vote with their own voting power or by voting power delegated to their projects? Ask the project owner to review your contributions!

Community-Driven Witness!

I am the first and only Steem Community-Driven Witness. Participate on Discord. Lets GROW TOGETHER!

mooncryption-utopian-witness-gif

Up-vote this comment to grow my power and help Open Source contributions like this one. Want to chat? Join me on Discord https://discord.gg/Pc8HG9x

oh man. I had set an alert to for when people post "get high". You've been blowing that up so much with these that I had to mute it. haha.

@prometheus21, Approve is not my ability, but I can upvote you.

This post has received a 1.95 % upvote from @boomerang thanks to: @prometheus21

This post has received a 3.13 % upvote from @drotto thanks to: @galasek.

Great post, please how can i request you help on a steemit related dev issue i am having

What kind of issue to you have?

You got a 67.78% upvote from @slimwhale courtesy of @prometheus21!

Did you know you can make a passive income by simply delegating steem power?
@slimwhale offers the best return on your investment, sharing 100% of the bidding pool rewards, daily, proportional to your investment.
Let's grow together, start earning now by clicking the following links: 10SP, | 50SP | 500SP, | any amount |
For more information, see here or join me on Discord

Coin Marketplace

STEEM 0.20
TRX 0.13
JST 0.029
BTC 67584.80
ETH 3438.61
USDT 1.00
SBD 2.70