mirror of
https://github.com/PeernetOfficial/core.git
synced 2026-07-17 02:47:51 +01:00
Add file metadata TagSharedByCount and TagSharedByGeoIP
This commit is contained in:
@@ -14,13 +14,15 @@ import (
|
||||
"time"
|
||||
)
|
||||
|
||||
// List of defined file tags.
|
||||
// List of defined file tags. Virtual tags are generated at runtime and are read-only. They cannot be stored on the blockchain.
|
||||
const (
|
||||
TagName = 0 // Name of file.
|
||||
TagFolder = 1 // Folder name.
|
||||
TagDescription = 2 // Arbitrary description of the file. May contain hashtags.
|
||||
TagDateShared = 3 // When the file was published on the blockchain. Cannot be set manually (virtual read-only tag).
|
||||
TagDateCreated = 4 // Date when the file was originally created. This may differ from the date in the block record, which indicates when the file was shared.
|
||||
TagName = 0 // Name of file.
|
||||
TagFolder = 1 // Folder name.
|
||||
TagDescription = 2 // Arbitrary description of the file. May contain hashtags.
|
||||
TagDateShared = 3 // When the file was published on the blockchain. Virtual.
|
||||
TagDateCreated = 4 // Date when the file was originally created. This may differ from the date in the block record, which indicates when the file was shared.
|
||||
TagSharedByCount = 5 // Count of peers that share the file. Virtual.
|
||||
TagSharedByGeoIP = 6 // GeoIP data of peers that are sharing the file. CSV encoded with header "latitude,longitude". Virtual.
|
||||
)
|
||||
|
||||
// Future tags to be defined for audio/video: Artist, Album, Title, Length, Bitrate, Codec
|
||||
@@ -43,9 +45,18 @@ func (tag *BlockRecordFileTag) Text() string {
|
||||
return string(tag.Data)
|
||||
}
|
||||
|
||||
// Number returns the tags data as uint64. It returns 0 if the data cannot be decoded.
|
||||
func (tag *BlockRecordFileTag) Number() uint64 {
|
||||
if len(tag.Data) != 8 {
|
||||
return 0
|
||||
}
|
||||
|
||||
return binary.LittleEndian.Uint64(tag.Data[0:8])
|
||||
}
|
||||
|
||||
// IsVirtual checks if the tag is virtual.
|
||||
func (tag *BlockRecordFileTag) IsVirtual() bool {
|
||||
return tag.Type == TagDateShared
|
||||
return IsTagVirtual(tag.Type)
|
||||
}
|
||||
|
||||
// TagFromDate returns a tag from date
|
||||
@@ -60,3 +71,21 @@ func TagFromDate(Type uint16, Date time.Time) BlockRecordFileTag {
|
||||
func TagFromText(Type uint16, Text string) BlockRecordFileTag {
|
||||
return BlockRecordFileTag{Type: Type, Data: []byte(Text)}
|
||||
}
|
||||
|
||||
// TagFromNumber returns a tag from a number
|
||||
func TagFromNumber(Type uint16, Number uint64) BlockRecordFileTag {
|
||||
var tempDate [8]byte
|
||||
binary.LittleEndian.PutUint64(tempDate[0:8], Number)
|
||||
|
||||
return BlockRecordFileTag{Type: Type, Data: tempDate[:]}
|
||||
}
|
||||
|
||||
// IsTagVirtual checks if the tag is a virtual one.
|
||||
func IsTagVirtual(Type uint16) bool {
|
||||
switch Type {
|
||||
case TagDateShared, TagSharedByCount, TagSharedByGeoIP:
|
||||
return true
|
||||
default:
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
@@ -91,9 +91,10 @@ type apiFileMetadata struct {
|
||||
Type uint16 `json:"type"` // See core.TagX constants.
|
||||
Name string `json:"name"` // User friendly name of the metadata type. Use the Type fields to identify the metadata as this name may change.
|
||||
// Depending on the exact type, one of the below fields is used for proper encoding:
|
||||
Text string `json:"text"` // Text value. UTF-8 encoding.
|
||||
Blob []byte `json:"blob"` // Binary data
|
||||
Date time.Time `json:"date"` // Date
|
||||
Text string `json:"text"` // Text value. UTF-8 encoding.
|
||||
Blob []byte `json:"blob"` // Binary data
|
||||
Date time.Time `json:"date"` // Date
|
||||
Number uint64 `json:"number"` // Number
|
||||
}
|
||||
|
||||
// apiBlockRecordFile is the metadata of a file published on the blockchain
|
||||
@@ -249,6 +250,12 @@ func blockRecordFileToAPI(input core.BlockRecordFile) (output apiBlockRecordFile
|
||||
date, _ := tag.Date()
|
||||
output.Metadata = append(output.Metadata, apiFileMetadata{Type: tag.Type, Name: "Date Created", Date: date})
|
||||
|
||||
case core.TagSharedByCount:
|
||||
output.Metadata = append(output.Metadata, apiFileMetadata{Type: tag.Type, Name: "Shared By Count", Number: tag.Number()})
|
||||
|
||||
case core.TagSharedByGeoIP:
|
||||
output.Metadata = append(output.Metadata, apiFileMetadata{Type: tag.Type, Name: "Shared By GeoIP", Text: tag.Text()})
|
||||
|
||||
default:
|
||||
output.Metadata = append(output.Metadata, apiFileMetadata{Type: tag.Type, Blob: tag.Data})
|
||||
}
|
||||
@@ -271,8 +278,12 @@ func blockRecordFileFromAPI(input apiBlockRecordFile) (output core.BlockRecordFi
|
||||
}
|
||||
|
||||
for _, meta := range input.Metadata {
|
||||
if core.IsTagVirtual(meta.Type) { // Virtual tags are not mapped back. They are read-only.
|
||||
continue
|
||||
}
|
||||
|
||||
switch meta.Type {
|
||||
case core.TagName, core.TagFolder, core.TagDescription, core.TagDateShared:
|
||||
case core.TagName, core.TagFolder, core.TagDescription: // auto mapped tags
|
||||
|
||||
case core.TagDateCreated:
|
||||
output.Tags = append(output.Tags, core.TagFromDate(meta.Type, meta.Date))
|
||||
|
||||
@@ -10,6 +10,7 @@ package webapi
|
||||
|
||||
import (
|
||||
"encoding/hex"
|
||||
"fmt"
|
||||
"math/rand"
|
||||
"sync"
|
||||
"time"
|
||||
@@ -284,20 +285,48 @@ func createTestResult(fileType int) (file core.BlockRecordFile) {
|
||||
extension = ".bin"
|
||||
}
|
||||
|
||||
file.Tags = append(file.Tags, core.TagFromText(core.TagName, TempFileName("", extension)))
|
||||
file.Tags = append(file.Tags, core.TagFromText(core.TagName, tempFileName("", extension)))
|
||||
//file.Tags = append(file.Tags, core.TagFromText(core.TagFolder, "not set"))
|
||||
file.Tags = append(file.Tags, core.TagFromDate(core.TagDateShared, time.Now().UTC()))
|
||||
|
||||
sharedByCount := uint64(rand.Intn(10))
|
||||
file.Tags = append(file.Tags, core.TagFromNumber(core.TagSharedByCount, sharedByCount))
|
||||
|
||||
if sharedByCount > 0 {
|
||||
var sharedByGeoIP string
|
||||
for n := uint64(0); n < sharedByCount; n++ {
|
||||
latitude, longitude := randomGeoIP()
|
||||
if n > 0 {
|
||||
sharedByGeoIP += "\n"
|
||||
}
|
||||
|
||||
sharedByGeoIP += fmt.Sprintf("%.4f", latitude) + "," + fmt.Sprintf("%.4f", longitude)
|
||||
}
|
||||
|
||||
file.Tags = append(file.Tags, core.TagFromText(core.TagSharedByGeoIP, sharedByGeoIP))
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// TempFileName generates a temporary filename for use in testing or whatever
|
||||
func TempFileName(prefix, suffix string) string {
|
||||
// tempFileName generates a temporary filename for use in testing
|
||||
func tempFileName(prefix, suffix string) string {
|
||||
randBytes := make([]byte, 16)
|
||||
rand.Read(randBytes)
|
||||
return prefix + hex.EncodeToString(randBytes) + "." + suffix
|
||||
}
|
||||
|
||||
// randomGeoIP generates random geo IP coordinates
|
||||
func randomGeoIP() (latitude, longitude float32) {
|
||||
// Latitude generates latitude (from -90.0 to 90.0)
|
||||
latitude = rand.Float32()*180 - 90
|
||||
|
||||
// Longitude generates longitude (from -180 to 180)
|
||||
longitude = rand.Float32()*360 - 180
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// queryRecentShared returns recently shared files on the network. fileType = -1 for any.
|
||||
func queryRecentShared(fileType, limit int) (files []*core.BlockRecordFile) {
|
||||
for n := 0; n < limit; n++ {
|
||||
|
||||
@@ -202,21 +202,24 @@ type apiFileMetadata struct {
|
||||
Type uint16 `json:"type"` // See core.TagX constants.
|
||||
Name string `json:"name"` // User friendly name of the metadata type. Use the Type fields to identify the metadata as this name may change.
|
||||
// Depending on the exact type, one of the below fields is used for proper encoding:
|
||||
Text string `json:"text"` // Text value. UTF-8 encoding.
|
||||
Blob []byte `json:"blob"` // Binary data
|
||||
Date time.Time `json:"date"` // Date
|
||||
Text string `json:"text"` // Text value. UTF-8 encoding.
|
||||
Blob []byte `json:"blob"` // Binary data
|
||||
Date time.Time `json:"date"` // Date
|
||||
Number uint64 `json:"number"` // Number
|
||||
}
|
||||
```
|
||||
|
||||
Below is the list of defined metadata types. Undefined types may be used by clients, but are always mapped into the `blob` field.
|
||||
Below is the list of defined metadata types. Undefined types may be used by clients, but are always mapped into the `blob` field. Virtual tags are generated at runtime and are read-only. They cannot be stored on the blockchain.
|
||||
|
||||
| Type | Constant | Encoding | Info |
|
||||
|------|----------------|----------|------------------------------------------------------------------------------------------------------------------------|
|
||||
| 0 | TagName | Text | Mapped into Name field. Name of file. |
|
||||
| 1 | TagFolder | Text | Mapped into Folder field. Folder name. |
|
||||
| 2 | TagDescription | Text | Mapped into Description field. Arbitrary description of the file. May contain hashtags. |
|
||||
| 3 | TagDateShared | Date | Mapped into Date field. When the file was published on the blockchain. Cannot be set manually (virtual read-only tag). |
|
||||
| 4 | TagDateCreated | Date | Date when the file was originally created. |
|
||||
| Type | Constant | Encoding | Virtual | Info |
|
||||
|------|----------------|----------|---------|------------------------------------------------------------------------------------------------------------------------|
|
||||
| 0 | TagName | Text | | Mapped into Name field. Name of file. |
|
||||
| 1 | TagFolder | Text | | Mapped into Folder field. Folder name. |
|
||||
| 2 | TagDescription | Text | | Mapped into Description field. Arbitrary description of the file. May contain hashtags. |
|
||||
| 3 | TagDateShared | Date | x | Mapped into Date field. When the file was published on the blockchain. |
|
||||
| 4 | TagDateCreated | Date | | Date when the file was originally created. |
|
||||
| 5 | TagSharedByCount | Number | x | Count of peers that share the file. |
|
||||
| 6 | TagSharedByGeoIP | Text/CSV | x | GeoIP data of peers that are sharing the file. CSV encoded with header "latitude,longitude". |
|
||||
|
||||
### Add File
|
||||
|
||||
@@ -570,7 +573,21 @@ Example response with dummy data:
|
||||
"description": "",
|
||||
"date": "2021-09-23T00:00:00Z",
|
||||
"nodeid": "j4yHzmCXiXqg4DPhowj0DIOuuyJxQflo2QSNG3yhCK8=",
|
||||
"metadata": []
|
||||
"metadata": [{
|
||||
"type": 5,
|
||||
"name": "Shared By Count",
|
||||
"text": "",
|
||||
"blob": null,
|
||||
"date": "0001-01-01T00:00:00Z",
|
||||
"number": 7
|
||||
}, {
|
||||
"type": 6,
|
||||
"name": "Shared By GeoIP",
|
||||
"text": "25.7766,-178.1275\n-46.4041,8.0066\n84.4478,8.2417\n14.1721,-9.7539\n-67.2364,127.6007\n-75.1604,106.7583\n70.5132,-133.4146",
|
||||
"blob": null,
|
||||
"date": "0001-01-01T00:00:00Z",
|
||||
"number": 0
|
||||
}]
|
||||
}]
|
||||
}
|
||||
```
|
||||
|
||||
Reference in New Issue
Block a user