summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--derelict.go10
-rw-r--r--esi.go56
-rw-r--r--models.go62
-rw-r--r--storage.go99
4 files changed, 186 insertions, 41 deletions
diff --git a/derelict.go b/derelict.go
index 2581d2f..569de51 100644
--- a/derelict.go
+++ b/derelict.go
@@ -57,9 +57,15 @@ func handleBattlesPost(w http.ResponseWriter, r *http.Request) {
return
}
decoder := json.NewDecoder(r.Body)
+ var stub BattleStub
+ if err := decoder.Decode(&stub); err != nil {
+ http.Error(w, "Error reading stub", http.StatusBadRequest)
+ return
+ }
var battle Battle
- if err := decoder.Decode(&battle); err != nil {
- http.Error(w, "Error reading battle", http.StatusBadRequest)
+ err = battle.From(&stub)
+ if err != nil {
+ http.Error(w, "Error getting battle details", http.StatusInternalServerError)
return
}
err = storage.AddBattle(&battle)
diff --git a/esi.go b/esi.go
index 4eaa682..bd3b0fe 100644
--- a/esi.go
+++ b/esi.go
@@ -20,6 +20,34 @@ func GetKillmail(id int32, hash string) (EsiKillmail, error) {
return details, nil
}
+func GetType(id int32) (EsiType, error) {
+ r, err := http.Get(fmt.Sprintf("https://esi.evetech.net/latest/universe/types/%d/", id))
+ if err != nil {
+ return EsiType{}, err
+ }
+ decoder := json.NewDecoder(r.Body)
+ var details EsiType
+ if err := decoder.Decode(&details); err != nil {
+ return EsiType{}, err
+ }
+
+ return details, nil
+}
+
+func GetGroup(id int32) (EsiGroup, error) {
+ r, err := http.Get(fmt.Sprintf("https://esi.evetech.net/latest/universe/groups/%d/", id))
+ if err != nil {
+ return EsiGroup{}, err
+ }
+ decoder := json.NewDecoder(r.Body)
+ var details EsiGroup
+ if err := decoder.Decode(&details); err != nil {
+ return EsiGroup{}, err
+ }
+
+ return details, nil
+}
+
func GetSolarSystem(id int32) (EsiUniverseSystem, error) {
r, err := http.Get(fmt.Sprintf("https://esi.evetech.net/latest/universe/systems/%d/", id))
if err != nil {
@@ -33,3 +61,31 @@ func GetSolarSystem(id int32) (EsiUniverseSystem, error) {
return details, nil
}
+
+func GetConstellation(id int32) (EsiUniverseConstellation, error) {
+ r, err := http.Get(fmt.Sprintf("https://esi.evetech.net/latest/universe/constellations/%d/", id))
+ if err != nil {
+ return EsiUniverseConstellation{}, err
+ }
+ decoder := json.NewDecoder(r.Body)
+ var details EsiUniverseConstellation
+ if err := decoder.Decode(&details); err != nil {
+ return EsiUniverseConstellation{}, err
+ }
+
+ return details, nil
+}
+
+func GetRegion(id int32) (EsiUniverseRegion, error) {
+ r, err := http.Get(fmt.Sprintf("https://esi.evetech.net/latest/universe/regions/%d/", id))
+ if err != nil {
+ return EsiUniverseRegion{}, err
+ }
+ decoder := json.NewDecoder(r.Body)
+ var details EsiUniverseRegion
+ if err := decoder.Decode(&details); err != nil {
+ return EsiUniverseRegion{}, err
+ }
+
+ return details, nil
+}
diff --git a/models.go b/models.go
index 7119fa9..3b369ca 100644
--- a/models.go
+++ b/models.go
@@ -15,29 +15,75 @@ type Killmail struct {
Hash string `json:"hash"`
}
+type Ship struct {
+ Name string `json:"name"`
+ Group string `json:"group"`
+}
+
+type Location struct {
+ Name string `json:"name"`
+ Security float32 `json:"security"`
+ Position Vector3 `json:"position"`
+ Constellation string `json:"constellation"`
+ Region string `json:"region"`
+}
+
type Team []int32
+type BattleStub struct {
+ Teams []Team `json:"teams"`
+ Killmails []Killmail `json:"killmails"`
+}
+
type Battle struct {
- Id string `json:"-"`
- LastModified time.Time `json:"-"`
- StartTime time.Time `json:"started_at"`
- EndTime time.Time `json:"ended_at"`
- Teams [2]Team `json:"teams"`
- Killmails []Killmail `json:"killmails"`
- Name string `json:"name"`
+ Id string `json:"-"`
+ Name string `json:"name"`
+ LastModified time.Time `json:"-"`
+ StartTime time.Time `json:"started_at"`
+ EndTime time.Time `json:"ended_at"`
+ Killmails []EsiKillmail `json:"killmails"` // How about no?
+ Teams []Team `json:"teams"`
+ Ships map[int32]Ship `json:"ships"`
+ Locations map[int32]Location `json:"locations"`
+ Names map[int32]string `json:"names'`
}
type EsiKillmail struct {
- SolarSystemId int32 `json:"solar_system_id"`
+ Id int32 `json:"killmail_id"`
+ Hash string `json:"hash"`
+ SolarSystemId int32 `json:"solar_system_id"`
Victim struct {
Position Vector3 `json:"position"`
ShipTypeId int32 `json:"ship_type_id"`
+ CharacterId int32 `json:"character_id"`
CorporationId int32 `json:"corporation_id"`
AllianceId int32 `json:"alliance_id"`
+ FactionId int32 `json:"faction_id"`
} `json:"victim"`
Time time.Time `json:"killmail_time"`
}
type EsiUniverseSystem struct {
+ Name string `json:"name"`
+ ConstellationId int32 `json:"constellation_id"`
+ Position Vector3 `json:"position"`
+ Security float32 `json:"security_status"`
+}
+
+type EsiUniverseConstellation struct {
+ Name string `json:"name"`
+ RegionId int32 `json:"region_id"`
+}
+
+type EsiUniverseRegion struct {
+ Name string `json:"name"`
+}
+
+type EsiType struct {
+ Name string `json:"name"`
+ GroupId int32 `json:"group_id"`
+}
+
+type EsiGroup struct {
Name string `json:"name"`
}
diff --git a/storage.go b/storage.go
index ee3489a..e57e0f2 100644
--- a/storage.go
+++ b/storage.go
@@ -36,7 +36,7 @@ func (s *Storage) CanPost(token string) (bool, error) {
return err == nil, nil
}
-func (b *Battle) CalculateHash() {
+func (b *BattleStub) CalculateHash() string {
hash := sha1.New()
killmails := b.Killmails
sort.Slice(killmails, func(lhs, rhs int) bool {
@@ -46,7 +46,73 @@ func (b *Battle) CalculateHash() {
fmt.Fprint(hash, km.Id)
}
sum := hash.Sum(nil)
- b.Id = hex.EncodeToString(sum[:])
+ return hex.EncodeToString(sum[:])
+}
+
+func (b *Battle) From(stub *BattleStub) error {
+ if len(stub.Killmails) < 1 {
+ return errors.New("missing killmails")
+ }
+ b.Id = stub.CalculateHash()
+ b.Ships = make(map[int32]Ship)
+ b.Locations = make(map[int32]Location)
+ b.Names = make(map[int32]string)
+ for _, km := range stub.Killmails {
+ details, err := GetKillmail(km.Id, km.Hash)
+ if err != nil {
+ return errors.New("could not retrieve killmail details")
+ }
+ details.Hash = km.Hash
+ b.Locations[details.SolarSystemId] = Location{}
+ b.Ships[details.Victim.ShipTypeId] = Ship{}
+ b.Names[details.Victim.CharacterId] = ""
+ b.Names[details.Victim.CorporationId] = ""
+ b.Names[details.Victim.AllianceId] = ""
+ b.Names[details.Victim.FactionId] = ""
+ if b.StartTime.IsZero() || b.StartTime.After(details.Time) {
+ b.StartTime = details.Time
+ }
+ if b.EndTime.IsZero() || b.EndTime.Before(details.Time) {
+ b.EndTime = details.Time
+ }
+ b.Killmails = append(b.Killmails, details)
+ }
+ b.Teams = stub.Teams
+ for key := range b.Ships {
+ t, err := GetType(key)
+ if err != nil {
+ return errors.New("could not retrieve type details")
+ }
+ g, err := GetGroup(t.GroupId)
+ if err != nil {
+ return errors.New("could not retrieve group details")
+ }
+ b.Ships[key] = Ship{Name: t.Name, Group: g.Name}
+ }
+ b.Name = "Untitled Fight"
+ for key := range b.Locations {
+ s, err := GetSolarSystem(key)
+ if err != nil {
+ return errors.New("could not retrieve solar system details")
+ }
+ c, err := GetConstellation(s.ConstellationId)
+ if err != nil {
+ return errors.New("could not retrieve constellation details")
+ }
+ r, err := GetRegion(c.RegionId)
+ if err != nil {
+ return errors.New("could not retrieve region details")
+ }
+ b.Locations[key] = Location{
+ Name: s.Name,
+ Security: s.Security,
+ Position: s.Position,
+ Constellation: c.Name,
+ Region: r.Name,
+ }
+ }
+ // TODO: Resolve Names
+ return nil
}
func (s *Storage) LoadBattle(battle *Battle) error {
@@ -63,35 +129,6 @@ func (s *Storage) LoadBattle(battle *Battle) error {
}
func (s *Storage) AddBattle(battle *Battle) error {
- if len(battle.Killmails) < 1 {
- return errors.New("missing killmails")
- }
- battle.CalculateHash()
- killmail := battle.Killmails[0]
- details, err := GetKillmail(killmail.Id, killmail.Hash)
- if err != nil {
- return err
- }
- system, err := GetSolarSystem(details.SolarSystemId)
- if err != nil {
- return err
- }
- battle.Name = fmt.Sprintf("Fight in %s", system.Name)
- battle.StartTime = details.Time
- battle.EndTime = details.Time
- for _, km := range battle.Killmails[1:] {
- details, err := GetKillmail(km.Id, km.Hash)
- if err != nil {
- return err
- }
- if battle.StartTime.After(details.Time) {
- battle.StartTime = details.Time
- }
- if battle.EndTime.Before(details.Time) {
- battle.EndTime = details.Time
- }
- }
-
data, err := json.Marshal(battle)
if err != nil {
return err