java.lang.Object
net.i2p.client.naming.NamingService
net.i2p.client.naming.SingleFileNamingService

public class SingleFileNamingServiceextends NamingService
A naming service based on a single file using the "hosts.txt" format. Supports adds, removes, and listeners.

All methods here are case-sensitive. Conversion to lower case is done in HostsTxtNamingService.

This does NOT provide .b32.i2p or {b64} resolution. It also does not do any caching. Use from HostsTxtNamingService or chain with another NamingService via MetaNamingService if you need those features.

  • Field Details

    • _file

      private final File _file
      The hosts file being read.
    • _fileLock

      private final ReentrantReadWriteLock _fileLock
      Guards reads and writes of the file.
    • _size

      private volatile int _size
      Cached number of entries.
    • _lastWrite

      private long _lastWrite
      Last write time.
    • _keyCache

      private final Map<String,String> _keyCache
      Hostname to base64 key cache, guarded by _fileLock; valid when _cacheStamp >= file mtime.
    • _cacheStamp

      private volatile long _cacheStamp
      File timestamp the current cache was read at.
    • _isClosed

      private volatile boolean _isClosed
      True once the service is closed.
  • Constructor Details

    • SingleFileNamingService

      public SingleFileNamingService(I2PAppContext context, String filename)
      Application context.
      Parameters:
      context - the application context
      filename - the hosts file name
  • Method Details

    • getName

      public String getName()
      Return the file's absolute path.
      Overrides:
      getName in class NamingService
      Returns:
      the file's absolute path
    • lookup

      public Destination lookup(String hostname, Properties lookupOptions, Properties storedOptions)
      Will strip a "www." prefix and retry if lookup fails.
      Specified by:
      lookup in class NamingService
      Parameters:
      hostname - case-sensitive; caller should convert to lower case
      lookupOptions - unused, may be null
      storedOptions - unused, may be null
      Returns:
      dest or null
    • reverseLookup

      public String reverseLookup(Destination dest, Properties options)
      Reverse lookup a destination to a hostname.
      Overrides:
      reverseLookup in class NamingService
      Parameters:
      dest - non-null destination to look up
      options - unused, may be null
      Returns:
      hostname or null
    • getKey

      private String getKey(String host) throws IOException
      Better than DataHelper.loadProps(), doesn't load the whole file into memory, and stops when it finds a match.
      Parameters:
      host - case-sensitive; caller should convert to lower case
      Returns:
      the base64 destination key mapped to that hostname in the hosts file, or null if the file holds no such entry
      Throws:
      IOException - if the hosts file changed and could not be re-read
    • loadKeyCacheLocked

      private void loadKeyCacheLocked() throws IOException
      Full-scan parse of the hosts file into _keyCache (hostname -> base64 key). Caller must hold the read lock. Sets _cacheStamp on success.
      Throws:
      IOException - if the hosts file exists but could not be read
    • put

      public boolean put(String hostname, Destination d, Properties options)
      Store a hostname-destination mapping.
      Overrides:
      put in class NamingService
      Parameters:
      hostname - case-sensitive; caller should convert to lower case
      d - the destination for the hostname
      options - if non-null, any prefixed with '=' will be appended in subscription format
      Returns:
      true if the entry was stored; this base implementation always returns false
    • putIfAbsent

      public boolean putIfAbsent(String hostname, Destination d, Properties options)
      Store a hostname-destination mapping if not already present.
      Overrides:
      putIfAbsent in class NamingService
      Parameters:
      hostname - case-sensitive; caller should convert to lower case
      d - the destination for the hostname
      options - if non-null, any prefixed with '=' will be appended in subscription format
      Returns:
      true if no entry existed and the new one was stored; this base implementation always returns false
    • writeOptions

      public static void writeOptions(Properties options, Writer out) throws IOException
      Write the subscription options part of the line (including the #!). Only options starting with '=' (if any) are written (with the '=' stripped). Does not write a newline.
      Parameters:
      options - non-null
      out - the writer to write to
      Throws:
      IOException - if the writer rejects the property data
    • remove

      public boolean remove(String hostname, Properties options)
      Remove a hostname from the naming service.
      Overrides:
      remove in class NamingService
      Parameters:
      hostname - case-sensitive; caller should convert to lower case
      options - unused, may be null
      Returns:
      true if removed successfully, false on error or if it did not exist
    • getEntries

      public Map<String, Destination> getEntries(Properties options)
      Return all entries matching the options.
      Overrides:
      getEntries in class NamingService
      Parameters:
      options - null OK, or as follows: Key "search": return only those matching substring Key "startsWith": return only those starting with ("[0-9]" allowed) Key "skip": number of matching entries to skip Key "limit": maximum number of matching entries to return
      Returns:
      the matching hostname to destination pairs, empty when the file does not exist
    • getBase64Entries

      public Map<String,String> getBase64Entries(Properties options)
      Overridden since we store base64 natively.
      Overrides:
      getBase64Entries in class NamingService
      Parameters:
      options - null OK, or as follows: Key "search": return only those matching substring Key "startsWith": return only those starting with ("[0-9]" allowed)
      Returns:
      all mappings (matching the options if non-null) or empty Map if none. Returned Map is not sorted.
    • export

      public void export(Writer out, Properties options) throws IOException
      Overridden for efficiency. Output is not sorted.
      Overrides:
      export in class NamingService
      Parameters:
      out - the writer to export to
      options - unused, may be null
      Throws:
      IOException - if an I/O error occurs
    • getNames

      public Set<String> getNames(Properties options)
      Return all known host names.
      Overrides:
      getNames in class NamingService
      Parameters:
      options - unused, may be null
      Returns:
      all known host names, unsorted
    • size

      public int size(Properties options)
      Return the number of entries.
      Overrides:
      size in class NamingService
      Parameters:
      options - unused, may be null
      Returns:
      number of entries (matching the options if non-null) or -1 if unknown
    • shutdown

      public void shutdown()
      Description copied from class: NamingService
      Parent will call when removed. If this is the root naming service, the core will stop it. Should not be called by others.
      Overrides:
      shutdown in class NamingService
    • getReadLock

      private void getReadLock()
      Takes the file read lock.
    • releaseReadLock

      private void releaseReadLock()
      Releases the file read lock.
    • getWriteLock

      private boolean getWriteLock()
      Try to acquire the write lock.
      Returns:
      true if the lock was acquired
    • releaseWriteLock

      private void releaseWriteLock()
      Releases the file write lock.
    • stripComment

      private static String stripComment(String line)
      Strip an end-of-line comment and trim surrounding whitespace.
      Parameters:
      line - a raw hosts file line
      Returns:
      the line up to (and not including) the first '#', trimmed
    • endsWithNewline

      private static boolean endsWithNewline(File file)
      Whether the file ends with a newline.
      Parameters:
      file - the file to inspect
      Returns:
      true if the file exists, is non-empty and ends with a newline