2020-04-29 17:38:04 +02:00
|
|
|
// Copyright (C) 2020 Opsmate, Inc.
|
|
|
|
//
|
|
|
|
// This Source Code Form is subject to the terms of the Mozilla
|
|
|
|
// Public License, v. 2.0. If a copy of the MPL was not distributed
|
|
|
|
// with this file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
|
|
|
//
|
|
|
|
// This software is distributed WITHOUT A WARRANTY OF ANY KIND.
|
|
|
|
// See the Mozilla Public License for details.
|
|
|
|
|
|
|
|
package loglist
|
|
|
|
|
|
|
|
import (
|
|
|
|
"time"
|
2021-04-30 23:04:16 +02:00
|
|
|
|
|
|
|
"software.sslmate.com/src/certspotter/ct"
|
2020-04-29 17:38:04 +02:00
|
|
|
)
|
|
|
|
|
|
|
|
type List struct {
|
2021-11-01 19:19:45 +01:00
|
|
|
Version string `json:"version"`
|
|
|
|
LogListTimestamp time.Time `json:"log_list_timestamp"` // Only present in v3 of schema
|
|
|
|
Operators []Operator `json:"operators"`
|
2020-04-29 17:38:04 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
type Operator struct {
|
2024-11-25 14:09:57 +01:00
|
|
|
Name string `json:"name"`
|
|
|
|
Email []string `json:"email"`
|
|
|
|
Logs []Log `json:"logs"`
|
|
|
|
TiledLogs []Log `json:"tiled_logs"`
|
2020-04-29 17:38:04 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
type Log struct {
|
2021-04-30 23:04:16 +02:00
|
|
|
Key []byte `json:"key"`
|
|
|
|
LogID ct.SHA256Hash `json:"log_id"`
|
|
|
|
MMD int `json:"mmd"`
|
2024-11-25 14:09:57 +01:00
|
|
|
URL string `json:"url,omitempty"` // only for rfc6962 logs
|
|
|
|
SubmissionURL string `json:"submission_url,omitempty"` // only for static-ct-api logs
|
|
|
|
MonitoringURL string `json:"monitoring_url,omitempty"` // only for static-ct-api logs
|
2021-04-30 23:04:16 +02:00
|
|
|
Description string `json:"description"`
|
|
|
|
State State `json:"state"`
|
|
|
|
DNS string `json:"dns"`
|
|
|
|
LogType LogType `json:"log_type"`
|
2020-04-29 17:38:04 +02:00
|
|
|
TemporalInterval *struct {
|
|
|
|
StartInclusive time.Time `json:"start_inclusive"`
|
|
|
|
EndExclusive time.Time `json:"end_exclusive"`
|
|
|
|
} `json:"temporal_interval"`
|
2021-11-01 19:19:45 +01:00
|
|
|
|
|
|
|
// TODO: add previous_operators
|
2020-04-29 17:38:04 +02:00
|
|
|
}
|
|
|
|
|
2024-11-25 14:09:57 +01:00
|
|
|
func (log *Log) IsRFC6962() bool { return log.URL != "" }
|
|
|
|
func (log *Log) IsStaticCTAPI() bool { return log.SubmissionURL != "" && log.MonitoringURL != "" }
|
|
|
|
|
|
|
|
// Return URL prefix for submission using the RFC6962 protocol
|
|
|
|
func (log *Log) GetSubmissionURL() string {
|
|
|
|
if log.SubmissionURL != "" {
|
|
|
|
return log.SubmissionURL
|
|
|
|
} else {
|
|
|
|
return log.URL
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Return URL prefix for monitoring.
|
|
|
|
// Since the protocol understood by the URL might be either RFC6962 or static-ct-api, this URL is
|
|
|
|
// only useful for informational purposes.
|
|
|
|
func (log *Log) GetMonitoringURL() string {
|
|
|
|
if log.MonitoringURL != "" {
|
|
|
|
return log.MonitoringURL
|
|
|
|
} else {
|
|
|
|
return log.URL
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-04-29 17:38:04 +02:00
|
|
|
type State struct {
|
|
|
|
Pending *struct {
|
|
|
|
Timestamp time.Time `json:"timestamp"`
|
|
|
|
} `json:"pending"`
|
|
|
|
|
|
|
|
Qualified *struct {
|
|
|
|
Timestamp time.Time `json:"timestamp"`
|
|
|
|
} `json:"qualified"`
|
|
|
|
|
|
|
|
Usable *struct {
|
|
|
|
Timestamp time.Time `json:"timestamp"`
|
|
|
|
} `json:"usable"`
|
|
|
|
|
|
|
|
Readonly *struct {
|
|
|
|
Timestamp time.Time `json:"timestamp"`
|
|
|
|
FinalTreeHead struct {
|
|
|
|
TreeSize int64 `json:"tree_size"`
|
|
|
|
SHA256RootHash []byte `json:"sha256_root_hash"`
|
|
|
|
} `json:"final_tree_head"`
|
|
|
|
} `json:"readonly"`
|
|
|
|
|
|
|
|
Retired *struct {
|
|
|
|
Timestamp time.Time `json:"timestamp"`
|
|
|
|
} `json:"retired"`
|
|
|
|
|
|
|
|
Rejected *struct {
|
|
|
|
Timestamp time.Time `json:"timestamp"`
|
|
|
|
} `json:"rejected"`
|
|
|
|
}
|
|
|
|
|
2021-05-01 23:35:18 +02:00
|
|
|
func (state *State) IsApproved() bool {
|
|
|
|
return state.Qualified != nil || state.Usable != nil || state.Readonly != nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (state *State) WasApprovedAt(t time.Time) bool {
|
|
|
|
return state.Retired != nil && t.Before(state.Retired.Timestamp)
|
|
|
|
}
|
|
|
|
|
2020-04-29 17:38:04 +02:00
|
|
|
type LogType string
|
|
|
|
|
|
|
|
const (
|
|
|
|
LogTypeProd = "prod"
|
|
|
|
LogTypeTest = "test"
|
|
|
|
)
|