jprop 0.2.0

no-std parser for java .properties files that actually works
Documentation
# jprop
no-std parser for java `.properties` files that actually works 

## Motivation
As everyone should be aware, there are at least a dozen .properties parsers
on crates.io; unfortunately, none of them work properly.

A glance into https://en.wikipedia.org/wiki/.properties should reveal 
that there are many things that can go wrong when trying to parse .properties files.

I have evaluated five different .properties parsers, and none of them are capable of parsing the
files I need to parse, so I have come to the conclusion that I sadly have to make my own parser...

## Core features
* 0 dependencies
* no-std (feature gated, default features use std to allow for decoding of `std::io::Read`)
* full UTF-8 and ISO-8859-1 encoding support
  * This means you can parse your file with special symbols without \u escaping them.
    * This is widespread in java resource bundles, and half the parsers on crates.io already fail here.
  * UTF-8 implements a similar fallback to ISO-8859-1 as java does
  * fyi: java 4 and older only supports ISO-8859-1
  * fyi: java 5 to 8 uses ISO-8859-1 by default but can be configured to use UTF-8
  * fyi: java 9 and newer uses UTF-8 by default and uses a fallback to read ISO-8859-1.

* decoding of 'byte' or 'string' sources
  * byte as in from an io::Read or `&[u8]` and friends
  * string as in from a `&str`

* decoding of comments
  * Yes, in some use-cases this is sadly relevant.

* document decoding
  * Into `Vec<(String, String)>` or `HashMap<String, String>` (std only),
  * Into `Vec<Element>` Element being an enum, which is either Comment or Key+Value pair.

* stream decoding
  * Trait-based callback that accepts essentially an `fn(Element) -> bool`
    * element being an enum, which is either Comment or Key+Value pair.
    * Return false to stop parsing!

+ errors contain position information
  + character index,
  + character in line,
  + line number

## Example Usage

Parse key, value as a `HashMap<String, String>`
```rust
use std::collections::HashMap;
use std::fs::File;

pub fn read_test_properties() {
    let mut file = File::open("test.properties").expect("Failed to parse file");
    let data: HashMap<String, String> = jprop::parse_utf8_to_map(&mut file).expect("Failed to parse file");
    //use data here
    //profit?
}
```

Parse the entire document as a stream.
```rust
use jprop::{Element, ParserPosition};
use std::fs::File;

//Your handler would probably have some fields and be more complex.
struct Handler;

impl jprop::PropertyHandler for Handler {
  fn handle(&mut self, position: &ParserPosition, value: Element) -> bool {
    println!("Position {}:{}", position.line+1, position.character_in_line+1);
    match value {
      Element::BlankLine => println!(),
      Element::Comment(text) => println!("{}", text),
      Element::Value(key, value) => println!("{} = {}", key, value),
    }
    true
  }
}

pub fn read_test_properties_as_stream() {
  let mut file = File::open("test.properties").expect("Failed to parse file");
  let mut handler = Handler;
  jprop::parse_utf8(&mut file, &mut handler).expect("Failed to parse file");
  // use handler here
}
```

Parse from a &str
```rust
use std::collections::HashMap;

pub fn read_properties_from_string() {
    let test = "abc=abc\nbcd=bcd\n#..."; //or 'include_str!("some_file.properties");' but that only works with utf-8 files.
    let data: HashMap<String, String> = jprop::parse_str_to_map(test).expect("Failed to parse str");
    //use data here
    //profit?
}
```