Clueless fool needs help with 'simple' code snippet

Hello there. I am a clueless code fool that is working a little project. The trouble is the project does involve a little coding which I know little about. I have tried messing with the code myself but after so many error messages decided to seek guidance.

The whole script will pull live data from an online API. The code I have is meant to filter the results displayed.

func processStash(stash *api.Stash) {
	for _, item := range stash.Items {
		if item.League == "Leaguename" && item.Type == "Itemname" {
			log.Printf("Item name: account = %v, league = %v, note = %v, tab = %v", stash.AccountName, item.League, item.Note, stash.Label)
		}
	}
}

The code I want to add to the function

re := regexp.MustCompile("^~b/o ([0-9\\.]+) ([^ ]+)$")
matches := re.FindStringSubmatch(item.Note)
if matches != nil {
    fmt.Printf("count = %v, currency = %v", matches[1], matches[2])

It should filter the results and just show results where item.Note is not empty or if I can show only results where item.Note = X.

Later on I would also like to make it so if a result that fits the criteria is found a pop box appears with information and maybe even a sound plays. That is something I plan to look into, I am not even sure if Go can do those things.

Hey @Spiffy1,

Are you simply just trying to further filter the results to match the note not empty and note == x criteria?

If so, you can just add another if condition to your loop for those checks and just ignore the items where the note doesn’t match what you want, for example:

for _, item := range stash.Items {
	if item.League == "Leaguename" && item.Type == "Itemname" {
		if item.Note == "" || item.Note != filterStr {
			continue
		}
		log.Printf("Item name: account = %v, league = %v, note = %v, tab = %v", stash.AccountName, item.League, item.Note, stash.Label)
	}
}

In that example, filterStr would be the string you’re searching for.

I prefer to structure this sort of thing as a series of filters with early continues.

func processStash(stash *api.Stash) {
	for _, item := range stash.Items {
		if item.League != "Leaguename" {
			continue
		}

		if item.Type != "Itemname" {
			continue
		}

		log.Printf("Item name: account = %v, league = %v, note = %v, tab = %v", stash.AccountName, item.League, item.Note, stash.Label)

		re := regexp.MustCompile("^~b/o ([0-9\\.]+) ([^ ]+)$")
		matches := re.FindStringSubmatch(item.Note)
		if matches != nil {
			fmt.Printf("count = %v, currency = %v", matches[1], matches[2])
		}
	}
}

While this lengthens the function, it makes adding/removing individual filters easier. Nesting depth and if statement complexity is also reduced, which IMHO makes the process easier to understand and debug.

Put filters that remove items from further consideration at the beginning, processing at the end. Performance can be optimized by ordering the filters by the number of items they are expected to remove or by the computation required to run the filter.

The trouble is that the item.Note contains a currency number. I want to filter the results to show say 35 and less than 35. Also the variable in item.Note contains the equivalent of cents and dollars so if I ask it to show say 35 cents or less I do not want it to inadvertently show 35 dollars and less.

Thanks you for reply though, it will still help.

Thank you for your reply Nathankerr, I really like the solution, easier to alter and understand. I altered my code though and I am getting an error message " undefined: regexp". I will just post all the code, maybe easier to understand what is going on.

package main

import (
	"encoding/json"
	"io/ioutil"
	"log"
	"net/http"
	"os"
	"os/signal"

	"github.com/ccbrown/poe-go/api"
)

// To begin receiving newly updated items immediately, we need to get a recent change id. poe.ninja
// can provide us with that.
func getRecentChangeId() (string, error) {
	resp, err := http.Get("http://api.poe.ninja/api/Data/GetStats")
	if err != nil {
		return "", err
	}
	defer resp.Body.Close()

	body, err := ioutil.ReadAll(resp.Body)
	if err != nil {
		return "", err
	}

	var stats struct {
		// There are a few more fields in the response, but we only care about this.
		NextChangeId string `json:"nextChangeId"`
	}
	if err := json.Unmarshal(body, &stats); err != nil {
		return "", err
	}

	return stats.NextChangeId, nil
}

// This is where we look through stashes for items of interest. For this example, we'll just log
// reliquary key activity. You might want to parse buyouts, play sounds, compose messages that you
// can send in whispers, etc.
func processStash(stash *api.Stash) {
	for _, item := range stash.Items {
		if item.League != "Legacy" {
			continue
		}

		if item.Type != "<<set:MS>><<set:M>><<set:S>>Primordial Harmony" {
			continue
		}

		log.Printf("Item name: account = %v, league = %v, note = %v, tab = %v", stash.AccountName, item.League, item.Note, stash.Label)

		re := regexp.MustCompile("^~b/o ([0-9\\.]+) ([^ ]+)$")
		matches := re.FindStringSubmatch(item.Note)
		if matches != nil {
			fmt.Printf("count = %v, currency = %v", matches[1], matches[2])
		}
	}
}

//item.Type == "<<set:MS>><<set:M>><<set:S>>Primordial Harmony"
//&& item.Note == "~b/o 1 chaos"

func main() {
	log.Printf("requesting a recent change id from poe.ninja...")
	recentChangeId, err := getRecentChangeId()
	if err != nil {
		log.Fatal(err)
	}
	log.Printf("starting with change id %v", recentChangeId)

	subscription := api.OpenPublicStashTabSubscription(recentChangeId)

	// If we get an interrupt signal (e.g. from control+c on the terminal), handle it gracefully.
	go func() {
		ch := make(chan os.Signal)
		signal.Notify(ch, os.Interrupt)
		<-ch
		log.Printf("shutting down")
		subscription.Close()

	}()

	// Loop forever over results.
	for result := range subscription.Channel {
		if result.Error != nil {
			log.Printf("error: %v", result.Error.Error())
			continue
		}
		for _, stash := range result.PublicStashTabs.Stashes {
			processStash(&stash)
		}
	}
}

The regexp package needs to be imported.

I setup my editor to use goimports on save. It will format the code like go fmt and will also automatically add and remove package imports as needed.

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.