github.com/philhug/dnscontrol@v0.2.4-0.20180625181521-921fa9849001/providers/capabilities.go (about)

     1  package providers
     2  
     3  import (
     4  	"log"
     5  )
     6  
     7  // Capability is a bitmasked set of "features" that a provider supports. Only use constants from this package.
     8  type Capability uint32
     9  
    10  const (
    11  	// If you add something to this list, you probably want to add it to pkg/normalize/validate.go checkProviderCapabilities() or somewhere near there.
    12  
    13  	// CanUseAlias indicates the provider support ALIAS records (or flattened CNAMES). Up to the provider to translate them to the appropriate record type.
    14  	CanUseAlias Capability = iota
    15  
    16  	// CanUseCAA indicates the provider can handle CAA records
    17  	CanUseCAA
    18  
    19  	// CanUsePTR indicates the provider can handle PTR records
    20  	CanUsePTR
    21  
    22  	// CanUseSRV indicates the provider can handle SRV records
    23  	CanUseSRV
    24  
    25  	// CanUseTLSA indicates the provider can handle TLSA records
    26  	CanUseTLSA
    27  
    28  	// CanUseTXTMulti indicates the provider can handle TXT records with multiple strings
    29  	CanUseTXTMulti
    30  
    31  	// CantUseNOPURGE indicates NO_PURGE is broken for this provider. To make it
    32  	// work would require complex emulation of an incremental update mechanism,
    33  	// so it is easier to simply mark this feature as not working for this
    34  	// provider.
    35  	CantUseNOPURGE
    36  
    37  	// DocOfficiallySupported means it is actively used and maintained by stack exchange
    38  	DocOfficiallySupported
    39  	// DocDualHost means provider allows full management of apex NS records, so we can safely dual-host with anothe provider
    40  	DocDualHost
    41  	// DocCreateDomains means provider can add domains with the `dnscontrol create-domains` command
    42  	DocCreateDomains
    43  
    44  	// CanUseRoute53Alias indicates the provider support the specific R53_ALIAS records that only the Route53 provider supports
    45  	CanUseRoute53Alias
    46  )
    47  
    48  var providerCapabilities = map[string]map[Capability]bool{}
    49  
    50  // ProviderHasCabability returns true if provider has capability.
    51  func ProviderHasCabability(pType string, cap Capability) bool {
    52  	if providerCapabilities[pType] == nil {
    53  		return false
    54  	}
    55  	return providerCapabilities[pType][cap]
    56  }
    57  
    58  // DocumentationNote is a way for providers to give more detail about what features they support.
    59  type DocumentationNote struct {
    60  	HasFeature    bool
    61  	Unimplemented bool
    62  	Comment       string
    63  	Link          string
    64  }
    65  
    66  // DocumentationNotes is a full list of notes for a single provider
    67  type DocumentationNotes map[Capability]*DocumentationNote
    68  
    69  // ProviderMetadata is a common interface for DocumentationNotes and Capability to be used interchangably
    70  type ProviderMetadata interface{}
    71  
    72  // Notes is a collection of all documentation notes, keyed by provider type
    73  var Notes = map[string]DocumentationNotes{}
    74  
    75  func unwrapProviderCapabilities(pName string, meta []ProviderMetadata) {
    76  	if providerCapabilities[pName] == nil {
    77  		providerCapabilities[pName] = map[Capability]bool{}
    78  	}
    79  	for _, pm := range meta {
    80  		switch x := pm.(type) {
    81  		case Capability:
    82  			providerCapabilities[pName][x] = true
    83  		case DocumentationNotes:
    84  			if Notes[pName] == nil {
    85  				Notes[pName] = DocumentationNotes{}
    86  			}
    87  			for k, v := range x {
    88  				Notes[pName][k] = v
    89  				providerCapabilities[pName][k] = v.HasFeature
    90  			}
    91  		default:
    92  			log.Fatalf("Unrecognized ProviderMetadata type: %T", pm)
    93  		}
    94  
    95  	}
    96  }
    97  
    98  // Can is a small helper for concisely creating Documentation Notes
    99  // comments are variadic for easy ommission. First is comment, second is link, the rest are ignored.
   100  func Can(comments ...string) *DocumentationNote {
   101  	n := &DocumentationNote{
   102  		HasFeature: true,
   103  	}
   104  	n.addStrings(comments)
   105  	return n
   106  }
   107  
   108  // Cannot is a small helper for concisely creating Documentation Notes
   109  // comments are variadic for easy ommission. First is comment, second is link, the rest are ignored.
   110  func Cannot(comments ...string) *DocumentationNote {
   111  	n := &DocumentationNote{
   112  		HasFeature: false,
   113  	}
   114  	n.addStrings(comments)
   115  	return n
   116  }
   117  
   118  // Unimplemented is a small helper for concisely creating Documentation Notes
   119  // comments are variadic for easy ommission. First is comment, second is link, the rest are ignored.
   120  func Unimplemented(comments ...string) *DocumentationNote {
   121  	n := &DocumentationNote{
   122  		HasFeature:    false,
   123  		Unimplemented: true,
   124  	}
   125  	n.addStrings(comments)
   126  	return n
   127  }
   128  
   129  func (n *DocumentationNote) addStrings(comments []string) {
   130  	if len(comments) > 0 {
   131  		n.Comment = comments[0]
   132  	}
   133  	if len(comments) > 1 {
   134  		n.Link = comments[1]
   135  	}
   136  }