├── .github └── CODEOWNERS ├── .gitignore ├── Cargo.lock ├── Cargo.toml ├── LICENSE ├── example.config.toml ├── migrations ├── 20200612002126_initial │ ├── down.sql │ └── up.sql ├── 20200612004225_antiflood │ ├── down.sql │ └── up.sql └── 20200612020854_message-field │ ├── down.sql │ └── up.sql ├── shell.nix └── src ├── database.rs ├── errors.rs ├── guards.rs ├── main.rs ├── routes ├── banlist.rs ├── mod.rs ├── root.rs └── tokens.rs ├── settings.rs ├── tests ├── mod.rs ├── root.rs └── tokens.rs └── utils.rs /.github/CODEOWNERS: -------------------------------------------------------------------------------- 1 | # Automatically request review for PRs 2 | 3 | * @SitiSchu 4 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | /target 2 | **/*.rs.bk 3 | 4 | .idea 5 | 6 | config.toml 7 | Migrant.toml 8 | -------------------------------------------------------------------------------- /Cargo.lock: -------------------------------------------------------------------------------- 1 | # This file is automatically @generated by Cargo. 2 | # It is not intended for manual editing. 3 | [[package]] 4 | name = "SpamWatchAPI" 5 | version = "0.4.0" 6 | dependencies = [ 7 | "actix-service 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", 8 | "actix-web 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)", 9 | "chrono 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 10 | "config 0.9.3 (registry+https://github.com/rust-lang/crates.io-index)", 11 | "dirs 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)", 12 | "failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 13 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 14 | "nanoid 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 15 | "postgres 0.17.0 (registry+https://github.com/rust-lang/crates.io-index)", 16 | "postgres-types 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 17 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 18 | "serde_json 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)", 19 | "slog 2.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 20 | "slog-async 2.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 21 | "slog-term 2.4.1 (registry+https://github.com/rust-lang/crates.io-index)", 22 | ] 23 | 24 | [[package]] 25 | name = "actix-codec" 26 | version = "0.1.2" 27 | source = "registry+https://github.com/rust-lang/crates.io-index" 28 | dependencies = [ 29 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 30 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 31 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 32 | "tokio-codec 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 33 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 34 | ] 35 | 36 | [[package]] 37 | name = "actix-connect" 38 | version = "0.2.0" 39 | source = "registry+https://github.com/rust-lang/crates.io-index" 40 | dependencies = [ 41 | "actix-codec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 42 | "actix-service 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", 43 | "actix-utils 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 44 | "derive_more 0.14.1 (registry+https://github.com/rust-lang/crates.io-index)", 45 | "either 1.5.2 (registry+https://github.com/rust-lang/crates.io-index)", 46 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 47 | "http 0.1.17 (registry+https://github.com/rust-lang/crates.io-index)", 48 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 49 | "tokio-current-thread 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 50 | "tokio-tcp 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 51 | "trust-dns-resolver 0.11.1 (registry+https://github.com/rust-lang/crates.io-index)", 52 | ] 53 | 54 | [[package]] 55 | name = "actix-http" 56 | version = "0.2.5" 57 | source = "registry+https://github.com/rust-lang/crates.io-index" 58 | dependencies = [ 59 | "actix-codec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 60 | "actix-connect 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 61 | "actix-server-config 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 62 | "actix-service 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", 63 | "actix-threadpool 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 64 | "actix-utils 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 65 | "base64 0.10.1 (registry+https://github.com/rust-lang/crates.io-index)", 66 | "bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 67 | "brotli2 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 68 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 69 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 70 | "chrono 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 71 | "copyless 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 72 | "derive_more 0.15.0 (registry+https://github.com/rust-lang/crates.io-index)", 73 | "either 1.5.2 (registry+https://github.com/rust-lang/crates.io-index)", 74 | "encoding_rs 0.8.17 (registry+https://github.com/rust-lang/crates.io-index)", 75 | "failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 76 | "flate2 1.0.9 (registry+https://github.com/rust-lang/crates.io-index)", 77 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 78 | "h2 0.1.25 (registry+https://github.com/rust-lang/crates.io-index)", 79 | "hashbrown 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 80 | "http 0.1.17 (registry+https://github.com/rust-lang/crates.io-index)", 81 | "httparse 1.3.4 (registry+https://github.com/rust-lang/crates.io-index)", 82 | "indexmap 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 83 | "language-tags 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 84 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 85 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 86 | "mime 0.3.13 (registry+https://github.com/rust-lang/crates.io-index)", 87 | "percent-encoding 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", 88 | "rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)", 89 | "regex 1.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 90 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 91 | "serde_json 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)", 92 | "serde_urlencoded 0.5.5 (registry+https://github.com/rust-lang/crates.io-index)", 93 | "sha1 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", 94 | "slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 95 | "time 0.1.42 (registry+https://github.com/rust-lang/crates.io-index)", 96 | "tokio-current-thread 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 97 | "tokio-tcp 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 98 | "tokio-timer 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", 99 | "trust-dns-resolver 0.11.1 (registry+https://github.com/rust-lang/crates.io-index)", 100 | ] 101 | 102 | [[package]] 103 | name = "actix-router" 104 | version = "0.1.5" 105 | source = "registry+https://github.com/rust-lang/crates.io-index" 106 | dependencies = [ 107 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 108 | "http 0.1.17 (registry+https://github.com/rust-lang/crates.io-index)", 109 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 110 | "regex 1.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 111 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 112 | "string 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 113 | ] 114 | 115 | [[package]] 116 | name = "actix-rt" 117 | version = "0.2.3" 118 | source = "registry+https://github.com/rust-lang/crates.io-index" 119 | dependencies = [ 120 | "actix-threadpool 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 121 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 122 | "tokio-current-thread 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 123 | "tokio-executor 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 124 | "tokio-reactor 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 125 | "tokio-timer 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", 126 | ] 127 | 128 | [[package]] 129 | name = "actix-server" 130 | version = "0.5.1" 131 | source = "registry+https://github.com/rust-lang/crates.io-index" 132 | dependencies = [ 133 | "actix-rt 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 134 | "actix-server-config 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 135 | "actix-service 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", 136 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 137 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 138 | "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)", 139 | "net2 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)", 140 | "num_cpus 1.10.1 (registry+https://github.com/rust-lang/crates.io-index)", 141 | "slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 142 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 143 | "tokio-reactor 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 144 | "tokio-signal 0.2.7 (registry+https://github.com/rust-lang/crates.io-index)", 145 | "tokio-tcp 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 146 | "tokio-timer 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", 147 | ] 148 | 149 | [[package]] 150 | name = "actix-server-config" 151 | version = "0.1.1" 152 | source = "registry+https://github.com/rust-lang/crates.io-index" 153 | dependencies = [ 154 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 155 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 156 | "tokio-tcp 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 157 | ] 158 | 159 | [[package]] 160 | name = "actix-service" 161 | version = "0.4.1" 162 | source = "registry+https://github.com/rust-lang/crates.io-index" 163 | dependencies = [ 164 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 165 | ] 166 | 167 | [[package]] 168 | name = "actix-threadpool" 169 | version = "0.1.1" 170 | source = "registry+https://github.com/rust-lang/crates.io-index" 171 | dependencies = [ 172 | "derive_more 0.14.1 (registry+https://github.com/rust-lang/crates.io-index)", 173 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 174 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 175 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 176 | "num_cpus 1.10.1 (registry+https://github.com/rust-lang/crates.io-index)", 177 | "parking_lot 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", 178 | "threadpool 1.7.1 (registry+https://github.com/rust-lang/crates.io-index)", 179 | ] 180 | 181 | [[package]] 182 | name = "actix-utils" 183 | version = "0.4.2" 184 | source = "registry+https://github.com/rust-lang/crates.io-index" 185 | dependencies = [ 186 | "actix-codec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 187 | "actix-service 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", 188 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 189 | "either 1.5.2 (registry+https://github.com/rust-lang/crates.io-index)", 190 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 191 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 192 | "tokio-current-thread 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 193 | "tokio-timer 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", 194 | ] 195 | 196 | [[package]] 197 | name = "actix-web" 198 | version = "1.0.3" 199 | source = "registry+https://github.com/rust-lang/crates.io-index" 200 | dependencies = [ 201 | "actix-codec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 202 | "actix-http 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", 203 | "actix-router 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 204 | "actix-rt 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 205 | "actix-server 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)", 206 | "actix-server-config 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 207 | "actix-service 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", 208 | "actix-threadpool 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 209 | "actix-utils 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 210 | "actix-web-codegen 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 211 | "awc 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 212 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 213 | "derive_more 0.15.0 (registry+https://github.com/rust-lang/crates.io-index)", 214 | "encoding_rs 0.8.17 (registry+https://github.com/rust-lang/crates.io-index)", 215 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 216 | "hashbrown 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 217 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 218 | "mime 0.3.13 (registry+https://github.com/rust-lang/crates.io-index)", 219 | "net2 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)", 220 | "parking_lot 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", 221 | "regex 1.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 222 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 223 | "serde_json 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)", 224 | "serde_urlencoded 0.5.5 (registry+https://github.com/rust-lang/crates.io-index)", 225 | "time 0.1.42 (registry+https://github.com/rust-lang/crates.io-index)", 226 | "url 1.7.2 (registry+https://github.com/rust-lang/crates.io-index)", 227 | ] 228 | 229 | [[package]] 230 | name = "actix-web-codegen" 231 | version = "0.1.2" 232 | source = "registry+https://github.com/rust-lang/crates.io-index" 233 | dependencies = [ 234 | "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", 235 | "syn 0.15.39 (registry+https://github.com/rust-lang/crates.io-index)", 236 | ] 237 | 238 | [[package]] 239 | name = "adler32" 240 | version = "1.0.3" 241 | source = "registry+https://github.com/rust-lang/crates.io-index" 242 | 243 | [[package]] 244 | name = "aho-corasick" 245 | version = "0.7.4" 246 | source = "registry+https://github.com/rust-lang/crates.io-index" 247 | dependencies = [ 248 | "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 249 | ] 250 | 251 | [[package]] 252 | name = "arc-swap" 253 | version = "0.3.11" 254 | source = "registry+https://github.com/rust-lang/crates.io-index" 255 | 256 | [[package]] 257 | name = "argon2rs" 258 | version = "0.2.5" 259 | source = "registry+https://github.com/rust-lang/crates.io-index" 260 | dependencies = [ 261 | "blake2-rfc 0.2.18 (registry+https://github.com/rust-lang/crates.io-index)", 262 | "scoped_threadpool 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 263 | ] 264 | 265 | [[package]] 266 | name = "arrayvec" 267 | version = "0.4.11" 268 | source = "registry+https://github.com/rust-lang/crates.io-index" 269 | dependencies = [ 270 | "nodrop 0.1.13 (registry+https://github.com/rust-lang/crates.io-index)", 271 | ] 272 | 273 | [[package]] 274 | name = "atty" 275 | version = "0.2.12" 276 | source = "registry+https://github.com/rust-lang/crates.io-index" 277 | dependencies = [ 278 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 279 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 280 | ] 281 | 282 | [[package]] 283 | name = "autocfg" 284 | version = "0.1.4" 285 | source = "registry+https://github.com/rust-lang/crates.io-index" 286 | 287 | [[package]] 288 | name = "awc" 289 | version = "0.2.2" 290 | source = "registry+https://github.com/rust-lang/crates.io-index" 291 | dependencies = [ 292 | "actix-codec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 293 | "actix-http 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", 294 | "actix-service 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", 295 | "base64 0.10.1 (registry+https://github.com/rust-lang/crates.io-index)", 296 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 297 | "derive_more 0.15.0 (registry+https://github.com/rust-lang/crates.io-index)", 298 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 299 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 300 | "mime 0.3.13 (registry+https://github.com/rust-lang/crates.io-index)", 301 | "percent-encoding 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", 302 | "rand 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 303 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 304 | "serde_json 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)", 305 | "serde_urlencoded 0.5.5 (registry+https://github.com/rust-lang/crates.io-index)", 306 | "tokio-timer 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", 307 | ] 308 | 309 | [[package]] 310 | name = "backtrace" 311 | version = "0.3.32" 312 | source = "registry+https://github.com/rust-lang/crates.io-index" 313 | dependencies = [ 314 | "backtrace-sys 0.1.30 (registry+https://github.com/rust-lang/crates.io-index)", 315 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 316 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 317 | "rustc-demangle 0.1.15 (registry+https://github.com/rust-lang/crates.io-index)", 318 | ] 319 | 320 | [[package]] 321 | name = "backtrace-sys" 322 | version = "0.1.30" 323 | source = "registry+https://github.com/rust-lang/crates.io-index" 324 | dependencies = [ 325 | "cc 1.0.37 (registry+https://github.com/rust-lang/crates.io-index)", 326 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 327 | ] 328 | 329 | [[package]] 330 | name = "base64" 331 | version = "0.10.1" 332 | source = "registry+https://github.com/rust-lang/crates.io-index" 333 | dependencies = [ 334 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 335 | ] 336 | 337 | [[package]] 338 | name = "base64" 339 | version = "0.11.0" 340 | source = "registry+https://github.com/rust-lang/crates.io-index" 341 | 342 | [[package]] 343 | name = "bitflags" 344 | version = "1.1.0" 345 | source = "registry+https://github.com/rust-lang/crates.io-index" 346 | 347 | [[package]] 348 | name = "blake2-rfc" 349 | version = "0.2.18" 350 | source = "registry+https://github.com/rust-lang/crates.io-index" 351 | dependencies = [ 352 | "arrayvec 0.4.11 (registry+https://github.com/rust-lang/crates.io-index)", 353 | "constant_time_eq 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 354 | ] 355 | 356 | [[package]] 357 | name = "block-buffer" 358 | version = "0.7.3" 359 | source = "registry+https://github.com/rust-lang/crates.io-index" 360 | dependencies = [ 361 | "block-padding 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 362 | "byte-tools 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 363 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 364 | "generic-array 0.12.3 (registry+https://github.com/rust-lang/crates.io-index)", 365 | ] 366 | 367 | [[package]] 368 | name = "block-padding" 369 | version = "0.1.4" 370 | source = "registry+https://github.com/rust-lang/crates.io-index" 371 | dependencies = [ 372 | "byte-tools 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 373 | ] 374 | 375 | [[package]] 376 | name = "brotli-sys" 377 | version = "0.3.2" 378 | source = "registry+https://github.com/rust-lang/crates.io-index" 379 | dependencies = [ 380 | "cc 1.0.37 (registry+https://github.com/rust-lang/crates.io-index)", 381 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 382 | ] 383 | 384 | [[package]] 385 | name = "brotli2" 386 | version = "0.3.2" 387 | source = "registry+https://github.com/rust-lang/crates.io-index" 388 | dependencies = [ 389 | "brotli-sys 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 390 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 391 | ] 392 | 393 | [[package]] 394 | name = "byte-tools" 395 | version = "0.3.1" 396 | source = "registry+https://github.com/rust-lang/crates.io-index" 397 | 398 | [[package]] 399 | name = "byteorder" 400 | version = "1.3.2" 401 | source = "registry+https://github.com/rust-lang/crates.io-index" 402 | 403 | [[package]] 404 | name = "bytes" 405 | version = "0.4.12" 406 | source = "registry+https://github.com/rust-lang/crates.io-index" 407 | dependencies = [ 408 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 409 | "iovec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 410 | ] 411 | 412 | [[package]] 413 | name = "bytes" 414 | version = "0.5.4" 415 | source = "registry+https://github.com/rust-lang/crates.io-index" 416 | 417 | [[package]] 418 | name = "c2-chacha" 419 | version = "0.2.2" 420 | source = "registry+https://github.com/rust-lang/crates.io-index" 421 | dependencies = [ 422 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 423 | "ppv-lite86 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", 424 | ] 425 | 426 | [[package]] 427 | name = "cc" 428 | version = "1.0.37" 429 | source = "registry+https://github.com/rust-lang/crates.io-index" 430 | 431 | [[package]] 432 | name = "cfg-if" 433 | version = "0.1.9" 434 | source = "registry+https://github.com/rust-lang/crates.io-index" 435 | 436 | [[package]] 437 | name = "chrono" 438 | version = "0.4.7" 439 | source = "registry+https://github.com/rust-lang/crates.io-index" 440 | dependencies = [ 441 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 442 | "num-integer 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)", 443 | "num-traits 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 444 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 445 | "time 0.1.42 (registry+https://github.com/rust-lang/crates.io-index)", 446 | ] 447 | 448 | [[package]] 449 | name = "cloudabi" 450 | version = "0.0.3" 451 | source = "registry+https://github.com/rust-lang/crates.io-index" 452 | dependencies = [ 453 | "bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 454 | ] 455 | 456 | [[package]] 457 | name = "config" 458 | version = "0.9.3" 459 | source = "registry+https://github.com/rust-lang/crates.io-index" 460 | dependencies = [ 461 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 462 | "nom 4.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 463 | "rust-ini 0.13.0 (registry+https://github.com/rust-lang/crates.io-index)", 464 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 465 | "serde-hjson 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)", 466 | "serde_json 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)", 467 | "toml 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)", 468 | "yaml-rust 0.4.3 (registry+https://github.com/rust-lang/crates.io-index)", 469 | ] 470 | 471 | [[package]] 472 | name = "constant_time_eq" 473 | version = "0.1.3" 474 | source = "registry+https://github.com/rust-lang/crates.io-index" 475 | 476 | [[package]] 477 | name = "copyless" 478 | version = "0.1.4" 479 | source = "registry+https://github.com/rust-lang/crates.io-index" 480 | 481 | [[package]] 482 | name = "crc32fast" 483 | version = "1.2.0" 484 | source = "registry+https://github.com/rust-lang/crates.io-index" 485 | dependencies = [ 486 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 487 | ] 488 | 489 | [[package]] 490 | name = "crossbeam-utils" 491 | version = "0.6.5" 492 | source = "registry+https://github.com/rust-lang/crates.io-index" 493 | dependencies = [ 494 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 495 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 496 | ] 497 | 498 | [[package]] 499 | name = "crypto-mac" 500 | version = "0.7.0" 501 | source = "registry+https://github.com/rust-lang/crates.io-index" 502 | dependencies = [ 503 | "generic-array 0.12.3 (registry+https://github.com/rust-lang/crates.io-index)", 504 | "subtle 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", 505 | ] 506 | 507 | [[package]] 508 | name = "derive_more" 509 | version = "0.14.1" 510 | source = "registry+https://github.com/rust-lang/crates.io-index" 511 | dependencies = [ 512 | "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", 513 | "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", 514 | "rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 515 | "syn 0.15.39 (registry+https://github.com/rust-lang/crates.io-index)", 516 | ] 517 | 518 | [[package]] 519 | name = "derive_more" 520 | version = "0.15.0" 521 | source = "registry+https://github.com/rust-lang/crates.io-index" 522 | dependencies = [ 523 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 524 | "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", 525 | "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", 526 | "regex 1.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 527 | "rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 528 | "syn 0.15.39 (registry+https://github.com/rust-lang/crates.io-index)", 529 | ] 530 | 531 | [[package]] 532 | name = "digest" 533 | version = "0.8.1" 534 | source = "registry+https://github.com/rust-lang/crates.io-index" 535 | dependencies = [ 536 | "generic-array 0.12.3 (registry+https://github.com/rust-lang/crates.io-index)", 537 | ] 538 | 539 | [[package]] 540 | name = "dirs" 541 | version = "1.0.5" 542 | source = "registry+https://github.com/rust-lang/crates.io-index" 543 | dependencies = [ 544 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 545 | "redox_users 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 546 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 547 | ] 548 | 549 | [[package]] 550 | name = "dirs" 551 | version = "2.0.1" 552 | source = "registry+https://github.com/rust-lang/crates.io-index" 553 | dependencies = [ 554 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 555 | "dirs-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", 556 | ] 557 | 558 | [[package]] 559 | name = "dirs-sys" 560 | version = "0.3.3" 561 | source = "registry+https://github.com/rust-lang/crates.io-index" 562 | dependencies = [ 563 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 564 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 565 | "redox_users 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 566 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 567 | ] 568 | 569 | [[package]] 570 | name = "dtoa" 571 | version = "0.4.4" 572 | source = "registry+https://github.com/rust-lang/crates.io-index" 573 | 574 | [[package]] 575 | name = "either" 576 | version = "1.5.2" 577 | source = "registry+https://github.com/rust-lang/crates.io-index" 578 | 579 | [[package]] 580 | name = "encoding" 581 | version = "0.2.33" 582 | source = "registry+https://github.com/rust-lang/crates.io-index" 583 | dependencies = [ 584 | "encoding-index-japanese 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)", 585 | "encoding-index-korean 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)", 586 | "encoding-index-simpchinese 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)", 587 | "encoding-index-singlebyte 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)", 588 | "encoding-index-tradchinese 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)", 589 | ] 590 | 591 | [[package]] 592 | name = "encoding-index-japanese" 593 | version = "1.20141219.5" 594 | source = "registry+https://github.com/rust-lang/crates.io-index" 595 | dependencies = [ 596 | "encoding_index_tests 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 597 | ] 598 | 599 | [[package]] 600 | name = "encoding-index-korean" 601 | version = "1.20141219.5" 602 | source = "registry+https://github.com/rust-lang/crates.io-index" 603 | dependencies = [ 604 | "encoding_index_tests 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 605 | ] 606 | 607 | [[package]] 608 | name = "encoding-index-simpchinese" 609 | version = "1.20141219.5" 610 | source = "registry+https://github.com/rust-lang/crates.io-index" 611 | dependencies = [ 612 | "encoding_index_tests 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 613 | ] 614 | 615 | [[package]] 616 | name = "encoding-index-singlebyte" 617 | version = "1.20141219.5" 618 | source = "registry+https://github.com/rust-lang/crates.io-index" 619 | dependencies = [ 620 | "encoding_index_tests 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 621 | ] 622 | 623 | [[package]] 624 | name = "encoding-index-tradchinese" 625 | version = "1.20141219.5" 626 | source = "registry+https://github.com/rust-lang/crates.io-index" 627 | dependencies = [ 628 | "encoding_index_tests 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 629 | ] 630 | 631 | [[package]] 632 | name = "encoding_index_tests" 633 | version = "0.1.4" 634 | source = "registry+https://github.com/rust-lang/crates.io-index" 635 | 636 | [[package]] 637 | name = "encoding_rs" 638 | version = "0.8.17" 639 | source = "registry+https://github.com/rust-lang/crates.io-index" 640 | dependencies = [ 641 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 642 | ] 643 | 644 | [[package]] 645 | name = "enum-as-inner" 646 | version = "0.2.1" 647 | source = "registry+https://github.com/rust-lang/crates.io-index" 648 | dependencies = [ 649 | "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", 650 | "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", 651 | "syn 0.15.39 (registry+https://github.com/rust-lang/crates.io-index)", 652 | ] 653 | 654 | [[package]] 655 | name = "failure" 656 | version = "0.1.5" 657 | source = "registry+https://github.com/rust-lang/crates.io-index" 658 | dependencies = [ 659 | "backtrace 0.3.32 (registry+https://github.com/rust-lang/crates.io-index)", 660 | "failure_derive 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 661 | ] 662 | 663 | [[package]] 664 | name = "failure_derive" 665 | version = "0.1.5" 666 | source = "registry+https://github.com/rust-lang/crates.io-index" 667 | dependencies = [ 668 | "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", 669 | "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", 670 | "syn 0.15.39 (registry+https://github.com/rust-lang/crates.io-index)", 671 | "synstructure 0.10.2 (registry+https://github.com/rust-lang/crates.io-index)", 672 | ] 673 | 674 | [[package]] 675 | name = "fake-simd" 676 | version = "0.1.2" 677 | source = "registry+https://github.com/rust-lang/crates.io-index" 678 | 679 | [[package]] 680 | name = "fallible-iterator" 681 | version = "0.2.0" 682 | source = "registry+https://github.com/rust-lang/crates.io-index" 683 | 684 | [[package]] 685 | name = "flate2" 686 | version = "1.0.9" 687 | source = "registry+https://github.com/rust-lang/crates.io-index" 688 | dependencies = [ 689 | "crc32fast 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 690 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 691 | "miniz-sys 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 692 | "miniz_oxide_c_api 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 693 | ] 694 | 695 | [[package]] 696 | name = "fnv" 697 | version = "1.0.6" 698 | source = "registry+https://github.com/rust-lang/crates.io-index" 699 | 700 | [[package]] 701 | name = "fuchsia-cprng" 702 | version = "0.1.1" 703 | source = "registry+https://github.com/rust-lang/crates.io-index" 704 | 705 | [[package]] 706 | name = "fuchsia-zircon" 707 | version = "0.3.3" 708 | source = "registry+https://github.com/rust-lang/crates.io-index" 709 | dependencies = [ 710 | "bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 711 | "fuchsia-zircon-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", 712 | ] 713 | 714 | [[package]] 715 | name = "fuchsia-zircon-sys" 716 | version = "0.3.3" 717 | source = "registry+https://github.com/rust-lang/crates.io-index" 718 | 719 | [[package]] 720 | name = "futures" 721 | version = "0.1.28" 722 | source = "registry+https://github.com/rust-lang/crates.io-index" 723 | 724 | [[package]] 725 | name = "futures" 726 | version = "0.3.1" 727 | source = "registry+https://github.com/rust-lang/crates.io-index" 728 | dependencies = [ 729 | "futures-channel 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 730 | "futures-core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 731 | "futures-executor 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 732 | "futures-io 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 733 | "futures-sink 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 734 | "futures-task 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 735 | "futures-util 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 736 | ] 737 | 738 | [[package]] 739 | name = "futures-channel" 740 | version = "0.3.1" 741 | source = "registry+https://github.com/rust-lang/crates.io-index" 742 | dependencies = [ 743 | "futures-core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 744 | "futures-sink 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 745 | ] 746 | 747 | [[package]] 748 | name = "futures-core" 749 | version = "0.3.1" 750 | source = "registry+https://github.com/rust-lang/crates.io-index" 751 | 752 | [[package]] 753 | name = "futures-executor" 754 | version = "0.3.1" 755 | source = "registry+https://github.com/rust-lang/crates.io-index" 756 | dependencies = [ 757 | "futures-core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 758 | "futures-task 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 759 | "futures-util 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 760 | ] 761 | 762 | [[package]] 763 | name = "futures-io" 764 | version = "0.3.1" 765 | source = "registry+https://github.com/rust-lang/crates.io-index" 766 | 767 | [[package]] 768 | name = "futures-macro" 769 | version = "0.3.1" 770 | source = "registry+https://github.com/rust-lang/crates.io-index" 771 | dependencies = [ 772 | "proc-macro-hack 0.5.11 (registry+https://github.com/rust-lang/crates.io-index)", 773 | "proc-macro2 1.0.8 (registry+https://github.com/rust-lang/crates.io-index)", 774 | "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 775 | "syn 1.0.14 (registry+https://github.com/rust-lang/crates.io-index)", 776 | ] 777 | 778 | [[package]] 779 | name = "futures-sink" 780 | version = "0.3.1" 781 | source = "registry+https://github.com/rust-lang/crates.io-index" 782 | 783 | [[package]] 784 | name = "futures-task" 785 | version = "0.3.1" 786 | source = "registry+https://github.com/rust-lang/crates.io-index" 787 | 788 | [[package]] 789 | name = "futures-util" 790 | version = "0.3.1" 791 | source = "registry+https://github.com/rust-lang/crates.io-index" 792 | dependencies = [ 793 | "futures-channel 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 794 | "futures-core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 795 | "futures-io 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 796 | "futures-macro 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 797 | "futures-sink 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 798 | "futures-task 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 799 | "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 800 | "pin-utils 0.1.0-alpha.4 (registry+https://github.com/rust-lang/crates.io-index)", 801 | "proc-macro-hack 0.5.11 (registry+https://github.com/rust-lang/crates.io-index)", 802 | "proc-macro-nested 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 803 | "slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 804 | ] 805 | 806 | [[package]] 807 | name = "generic-array" 808 | version = "0.12.3" 809 | source = "registry+https://github.com/rust-lang/crates.io-index" 810 | dependencies = [ 811 | "typenum 1.11.2 (registry+https://github.com/rust-lang/crates.io-index)", 812 | ] 813 | 814 | [[package]] 815 | name = "generic-array" 816 | version = "0.13.2" 817 | source = "registry+https://github.com/rust-lang/crates.io-index" 818 | dependencies = [ 819 | "typenum 1.11.2 (registry+https://github.com/rust-lang/crates.io-index)", 820 | ] 821 | 822 | [[package]] 823 | name = "getrandom" 824 | version = "0.1.6" 825 | source = "registry+https://github.com/rust-lang/crates.io-index" 826 | dependencies = [ 827 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 828 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 829 | ] 830 | 831 | [[package]] 832 | name = "h2" 833 | version = "0.1.25" 834 | source = "registry+https://github.com/rust-lang/crates.io-index" 835 | dependencies = [ 836 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 837 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 838 | "fnv 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)", 839 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 840 | "http 0.1.17 (registry+https://github.com/rust-lang/crates.io-index)", 841 | "indexmap 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 842 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 843 | "slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 844 | "string 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 845 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 846 | ] 847 | 848 | [[package]] 849 | name = "hashbrown" 850 | version = "0.5.0" 851 | source = "registry+https://github.com/rust-lang/crates.io-index" 852 | 853 | [[package]] 854 | name = "hmac" 855 | version = "0.7.1" 856 | source = "registry+https://github.com/rust-lang/crates.io-index" 857 | dependencies = [ 858 | "crypto-mac 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 859 | "digest 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)", 860 | ] 861 | 862 | [[package]] 863 | name = "hostname" 864 | version = "0.1.5" 865 | source = "registry+https://github.com/rust-lang/crates.io-index" 866 | dependencies = [ 867 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 868 | "winutil 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 869 | ] 870 | 871 | [[package]] 872 | name = "http" 873 | version = "0.1.17" 874 | source = "registry+https://github.com/rust-lang/crates.io-index" 875 | dependencies = [ 876 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 877 | "fnv 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)", 878 | "itoa 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)", 879 | ] 880 | 881 | [[package]] 882 | name = "httparse" 883 | version = "1.3.4" 884 | source = "registry+https://github.com/rust-lang/crates.io-index" 885 | 886 | [[package]] 887 | name = "idna" 888 | version = "0.1.5" 889 | source = "registry+https://github.com/rust-lang/crates.io-index" 890 | dependencies = [ 891 | "matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 892 | "unicode-bidi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", 893 | "unicode-normalization 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 894 | ] 895 | 896 | [[package]] 897 | name = "indexmap" 898 | version = "1.0.2" 899 | source = "registry+https://github.com/rust-lang/crates.io-index" 900 | 901 | [[package]] 902 | name = "iovec" 903 | version = "0.1.2" 904 | source = "registry+https://github.com/rust-lang/crates.io-index" 905 | dependencies = [ 906 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 907 | "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 908 | ] 909 | 910 | [[package]] 911 | name = "ipconfig" 912 | version = "0.2.1" 913 | source = "registry+https://github.com/rust-lang/crates.io-index" 914 | dependencies = [ 915 | "socket2 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)", 916 | "widestring 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 917 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 918 | "winreg 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", 919 | ] 920 | 921 | [[package]] 922 | name = "itoa" 923 | version = "0.4.4" 924 | source = "registry+https://github.com/rust-lang/crates.io-index" 925 | 926 | [[package]] 927 | name = "kernel32-sys" 928 | version = "0.2.2" 929 | source = "registry+https://github.com/rust-lang/crates.io-index" 930 | dependencies = [ 931 | "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 932 | "winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 933 | ] 934 | 935 | [[package]] 936 | name = "language-tags" 937 | version = "0.2.2" 938 | source = "registry+https://github.com/rust-lang/crates.io-index" 939 | 940 | [[package]] 941 | name = "lazy_static" 942 | version = "0.2.11" 943 | source = "registry+https://github.com/rust-lang/crates.io-index" 944 | 945 | [[package]] 946 | name = "lazy_static" 947 | version = "1.3.0" 948 | source = "registry+https://github.com/rust-lang/crates.io-index" 949 | dependencies = [ 950 | "spin 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 951 | ] 952 | 953 | [[package]] 954 | name = "libc" 955 | version = "0.2.59" 956 | source = "registry+https://github.com/rust-lang/crates.io-index" 957 | 958 | [[package]] 959 | name = "linked-hash-map" 960 | version = "0.3.0" 961 | source = "registry+https://github.com/rust-lang/crates.io-index" 962 | dependencies = [ 963 | "serde 0.8.23 (registry+https://github.com/rust-lang/crates.io-index)", 964 | "serde_test 0.8.23 (registry+https://github.com/rust-lang/crates.io-index)", 965 | ] 966 | 967 | [[package]] 968 | name = "linked-hash-map" 969 | version = "0.5.2" 970 | source = "registry+https://github.com/rust-lang/crates.io-index" 971 | 972 | [[package]] 973 | name = "lock_api" 974 | version = "0.1.5" 975 | source = "registry+https://github.com/rust-lang/crates.io-index" 976 | dependencies = [ 977 | "owning_ref 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 978 | "scopeguard 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", 979 | ] 980 | 981 | [[package]] 982 | name = "lock_api" 983 | version = "0.2.0" 984 | source = "registry+https://github.com/rust-lang/crates.io-index" 985 | dependencies = [ 986 | "scopeguard 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", 987 | ] 988 | 989 | [[package]] 990 | name = "lock_api" 991 | version = "0.3.3" 992 | source = "registry+https://github.com/rust-lang/crates.io-index" 993 | dependencies = [ 994 | "scopeguard 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", 995 | ] 996 | 997 | [[package]] 998 | name = "log" 999 | version = "0.4.7" 1000 | source = "registry+https://github.com/rust-lang/crates.io-index" 1001 | dependencies = [ 1002 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 1003 | ] 1004 | 1005 | [[package]] 1006 | name = "lru-cache" 1007 | version = "0.1.2" 1008 | source = "registry+https://github.com/rust-lang/crates.io-index" 1009 | dependencies = [ 1010 | "linked-hash-map 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)", 1011 | ] 1012 | 1013 | [[package]] 1014 | name = "matches" 1015 | version = "0.1.8" 1016 | source = "registry+https://github.com/rust-lang/crates.io-index" 1017 | 1018 | [[package]] 1019 | name = "md5" 1020 | version = "0.7.0" 1021 | source = "registry+https://github.com/rust-lang/crates.io-index" 1022 | 1023 | [[package]] 1024 | name = "memchr" 1025 | version = "2.2.1" 1026 | source = "registry+https://github.com/rust-lang/crates.io-index" 1027 | 1028 | [[package]] 1029 | name = "mime" 1030 | version = "0.3.13" 1031 | source = "registry+https://github.com/rust-lang/crates.io-index" 1032 | dependencies = [ 1033 | "unicase 2.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1034 | ] 1035 | 1036 | [[package]] 1037 | name = "miniz-sys" 1038 | version = "0.1.12" 1039 | source = "registry+https://github.com/rust-lang/crates.io-index" 1040 | dependencies = [ 1041 | "cc 1.0.37 (registry+https://github.com/rust-lang/crates.io-index)", 1042 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1043 | ] 1044 | 1045 | [[package]] 1046 | name = "miniz_oxide" 1047 | version = "0.2.2" 1048 | source = "registry+https://github.com/rust-lang/crates.io-index" 1049 | dependencies = [ 1050 | "adler32 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)", 1051 | ] 1052 | 1053 | [[package]] 1054 | name = "miniz_oxide_c_api" 1055 | version = "0.2.2" 1056 | source = "registry+https://github.com/rust-lang/crates.io-index" 1057 | dependencies = [ 1058 | "cc 1.0.37 (registry+https://github.com/rust-lang/crates.io-index)", 1059 | "crc32fast 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1060 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1061 | "miniz_oxide 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 1062 | ] 1063 | 1064 | [[package]] 1065 | name = "mio" 1066 | version = "0.6.21" 1067 | source = "registry+https://github.com/rust-lang/crates.io-index" 1068 | dependencies = [ 1069 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 1070 | "fuchsia-zircon 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", 1071 | "fuchsia-zircon-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", 1072 | "iovec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 1073 | "kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 1074 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1075 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 1076 | "miow 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 1077 | "net2 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)", 1078 | "slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 1079 | "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 1080 | ] 1081 | 1082 | [[package]] 1083 | name = "mio-uds" 1084 | version = "0.6.7" 1085 | source = "registry+https://github.com/rust-lang/crates.io-index" 1086 | dependencies = [ 1087 | "iovec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 1088 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1089 | "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)", 1090 | ] 1091 | 1092 | [[package]] 1093 | name = "miow" 1094 | version = "0.2.1" 1095 | source = "registry+https://github.com/rust-lang/crates.io-index" 1096 | dependencies = [ 1097 | "kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 1098 | "net2 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)", 1099 | "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 1100 | "ws2_32-sys 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 1101 | ] 1102 | 1103 | [[package]] 1104 | name = "nanoid" 1105 | version = "0.2.0" 1106 | source = "registry+https://github.com/rust-lang/crates.io-index" 1107 | dependencies = [ 1108 | "rand 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)", 1109 | ] 1110 | 1111 | [[package]] 1112 | name = "net2" 1113 | version = "0.2.33" 1114 | source = "registry+https://github.com/rust-lang/crates.io-index" 1115 | dependencies = [ 1116 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 1117 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1118 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1119 | ] 1120 | 1121 | [[package]] 1122 | name = "nodrop" 1123 | version = "0.1.13" 1124 | source = "registry+https://github.com/rust-lang/crates.io-index" 1125 | 1126 | [[package]] 1127 | name = "nom" 1128 | version = "4.2.3" 1129 | source = "registry+https://github.com/rust-lang/crates.io-index" 1130 | dependencies = [ 1131 | "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 1132 | "version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 1133 | ] 1134 | 1135 | [[package]] 1136 | name = "num-integer" 1137 | version = "0.1.41" 1138 | source = "registry+https://github.com/rust-lang/crates.io-index" 1139 | dependencies = [ 1140 | "autocfg 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1141 | "num-traits 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 1142 | ] 1143 | 1144 | [[package]] 1145 | name = "num-traits" 1146 | version = "0.1.43" 1147 | source = "registry+https://github.com/rust-lang/crates.io-index" 1148 | dependencies = [ 1149 | "num-traits 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 1150 | ] 1151 | 1152 | [[package]] 1153 | name = "num-traits" 1154 | version = "0.2.8" 1155 | source = "registry+https://github.com/rust-lang/crates.io-index" 1156 | dependencies = [ 1157 | "autocfg 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1158 | ] 1159 | 1160 | [[package]] 1161 | name = "num_cpus" 1162 | version = "1.10.1" 1163 | source = "registry+https://github.com/rust-lang/crates.io-index" 1164 | dependencies = [ 1165 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1166 | ] 1167 | 1168 | [[package]] 1169 | name = "opaque-debug" 1170 | version = "0.2.3" 1171 | source = "registry+https://github.com/rust-lang/crates.io-index" 1172 | 1173 | [[package]] 1174 | name = "owning_ref" 1175 | version = "0.4.0" 1176 | source = "registry+https://github.com/rust-lang/crates.io-index" 1177 | dependencies = [ 1178 | "stable_deref_trait 1.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 1179 | ] 1180 | 1181 | [[package]] 1182 | name = "parking_lot" 1183 | version = "0.7.1" 1184 | source = "registry+https://github.com/rust-lang/crates.io-index" 1185 | dependencies = [ 1186 | "lock_api 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 1187 | "parking_lot_core 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1188 | ] 1189 | 1190 | [[package]] 1191 | name = "parking_lot" 1192 | version = "0.8.0" 1193 | source = "registry+https://github.com/rust-lang/crates.io-index" 1194 | dependencies = [ 1195 | "lock_api 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1196 | "parking_lot_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 1197 | "rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 1198 | ] 1199 | 1200 | [[package]] 1201 | name = "parking_lot" 1202 | version = "0.10.0" 1203 | source = "registry+https://github.com/rust-lang/crates.io-index" 1204 | dependencies = [ 1205 | "lock_api 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", 1206 | "parking_lot_core 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 1207 | ] 1208 | 1209 | [[package]] 1210 | name = "parking_lot_core" 1211 | version = "0.4.0" 1212 | source = "registry+https://github.com/rust-lang/crates.io-index" 1213 | dependencies = [ 1214 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1215 | "rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)", 1216 | "rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 1217 | "smallvec 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", 1218 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1219 | ] 1220 | 1221 | [[package]] 1222 | name = "parking_lot_core" 1223 | version = "0.5.0" 1224 | source = "registry+https://github.com/rust-lang/crates.io-index" 1225 | dependencies = [ 1226 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 1227 | "cloudabi 0.0.3 (registry+https://github.com/rust-lang/crates.io-index)", 1228 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1229 | "rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)", 1230 | "redox_syscall 0.1.56 (registry+https://github.com/rust-lang/crates.io-index)", 1231 | "rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 1232 | "smallvec 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", 1233 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1234 | ] 1235 | 1236 | [[package]] 1237 | name = "parking_lot_core" 1238 | version = "0.7.0" 1239 | source = "registry+https://github.com/rust-lang/crates.io-index" 1240 | dependencies = [ 1241 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 1242 | "cloudabi 0.0.3 (registry+https://github.com/rust-lang/crates.io-index)", 1243 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1244 | "redox_syscall 0.1.56 (registry+https://github.com/rust-lang/crates.io-index)", 1245 | "smallvec 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1246 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1247 | ] 1248 | 1249 | [[package]] 1250 | name = "percent-encoding" 1251 | version = "1.0.1" 1252 | source = "registry+https://github.com/rust-lang/crates.io-index" 1253 | 1254 | [[package]] 1255 | name = "percent-encoding" 1256 | version = "2.1.0" 1257 | source = "registry+https://github.com/rust-lang/crates.io-index" 1258 | 1259 | [[package]] 1260 | name = "phf" 1261 | version = "0.8.0" 1262 | source = "registry+https://github.com/rust-lang/crates.io-index" 1263 | dependencies = [ 1264 | "phf_shared 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", 1265 | ] 1266 | 1267 | [[package]] 1268 | name = "phf_shared" 1269 | version = "0.8.0" 1270 | source = "registry+https://github.com/rust-lang/crates.io-index" 1271 | dependencies = [ 1272 | "siphasher 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1273 | ] 1274 | 1275 | [[package]] 1276 | name = "pin-project-lite" 1277 | version = "0.1.4" 1278 | source = "registry+https://github.com/rust-lang/crates.io-index" 1279 | 1280 | [[package]] 1281 | name = "pin-utils" 1282 | version = "0.1.0-alpha.4" 1283 | source = "registry+https://github.com/rust-lang/crates.io-index" 1284 | 1285 | [[package]] 1286 | name = "postgres" 1287 | version = "0.17.0" 1288 | source = "registry+https://github.com/rust-lang/crates.io-index" 1289 | dependencies = [ 1290 | "bytes 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)", 1291 | "fallible-iterator 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1292 | "futures 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1293 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 1294 | "tokio 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", 1295 | "tokio-postgres 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)", 1296 | ] 1297 | 1298 | [[package]] 1299 | name = "postgres-derive" 1300 | version = "0.4.0" 1301 | source = "registry+https://github.com/rust-lang/crates.io-index" 1302 | dependencies = [ 1303 | "proc-macro2 1.0.8 (registry+https://github.com/rust-lang/crates.io-index)", 1304 | "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 1305 | "syn 1.0.14 (registry+https://github.com/rust-lang/crates.io-index)", 1306 | ] 1307 | 1308 | [[package]] 1309 | name = "postgres-protocol" 1310 | version = "0.5.0" 1311 | source = "registry+https://github.com/rust-lang/crates.io-index" 1312 | dependencies = [ 1313 | "base64 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)", 1314 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 1315 | "bytes 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)", 1316 | "fallible-iterator 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1317 | "generic-array 0.13.2 (registry+https://github.com/rust-lang/crates.io-index)", 1318 | "hmac 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)", 1319 | "md5 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 1320 | "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 1321 | "rand 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 1322 | "sha2 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", 1323 | "stringprep 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 1324 | ] 1325 | 1326 | [[package]] 1327 | name = "postgres-types" 1328 | version = "0.1.0" 1329 | source = "registry+https://github.com/rust-lang/crates.io-index" 1330 | dependencies = [ 1331 | "bytes 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)", 1332 | "chrono 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 1333 | "fallible-iterator 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1334 | "postgres-derive 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1335 | "postgres-protocol 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 1336 | ] 1337 | 1338 | [[package]] 1339 | name = "ppv-lite86" 1340 | version = "0.2.5" 1341 | source = "registry+https://github.com/rust-lang/crates.io-index" 1342 | 1343 | [[package]] 1344 | name = "proc-macro-hack" 1345 | version = "0.5.11" 1346 | source = "registry+https://github.com/rust-lang/crates.io-index" 1347 | dependencies = [ 1348 | "proc-macro2 1.0.8 (registry+https://github.com/rust-lang/crates.io-index)", 1349 | "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 1350 | "syn 1.0.14 (registry+https://github.com/rust-lang/crates.io-index)", 1351 | ] 1352 | 1353 | [[package]] 1354 | name = "proc-macro-nested" 1355 | version = "0.1.3" 1356 | source = "registry+https://github.com/rust-lang/crates.io-index" 1357 | 1358 | [[package]] 1359 | name = "proc-macro2" 1360 | version = "0.4.30" 1361 | source = "registry+https://github.com/rust-lang/crates.io-index" 1362 | dependencies = [ 1363 | "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1364 | ] 1365 | 1366 | [[package]] 1367 | name = "proc-macro2" 1368 | version = "1.0.8" 1369 | source = "registry+https://github.com/rust-lang/crates.io-index" 1370 | dependencies = [ 1371 | "unicode-xid 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1372 | ] 1373 | 1374 | [[package]] 1375 | name = "quick-error" 1376 | version = "1.2.2" 1377 | source = "registry+https://github.com/rust-lang/crates.io-index" 1378 | 1379 | [[package]] 1380 | name = "quote" 1381 | version = "0.6.13" 1382 | source = "registry+https://github.com/rust-lang/crates.io-index" 1383 | dependencies = [ 1384 | "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", 1385 | ] 1386 | 1387 | [[package]] 1388 | name = "quote" 1389 | version = "1.0.2" 1390 | source = "registry+https://github.com/rust-lang/crates.io-index" 1391 | dependencies = [ 1392 | "proc-macro2 1.0.8 (registry+https://github.com/rust-lang/crates.io-index)", 1393 | ] 1394 | 1395 | [[package]] 1396 | name = "rand" 1397 | version = "0.4.6" 1398 | source = "registry+https://github.com/rust-lang/crates.io-index" 1399 | dependencies = [ 1400 | "fuchsia-cprng 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 1401 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1402 | "rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1403 | "rdrand 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1404 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1405 | ] 1406 | 1407 | [[package]] 1408 | name = "rand" 1409 | version = "0.6.5" 1410 | source = "registry+https://github.com/rust-lang/crates.io-index" 1411 | dependencies = [ 1412 | "autocfg 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1413 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1414 | "rand_chacha 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 1415 | "rand_core 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1416 | "rand_hc 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1417 | "rand_isaac 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 1418 | "rand_jitter 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1419 | "rand_os 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 1420 | "rand_pcg 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 1421 | "rand_xorshift 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 1422 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1423 | ] 1424 | 1425 | [[package]] 1426 | name = "rand" 1427 | version = "0.7.0" 1428 | source = "registry+https://github.com/rust-lang/crates.io-index" 1429 | dependencies = [ 1430 | "getrandom 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 1431 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1432 | "rand_chacha 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1433 | "rand_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 1434 | "rand_hc 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1435 | ] 1436 | 1437 | [[package]] 1438 | name = "rand_chacha" 1439 | version = "0.1.1" 1440 | source = "registry+https://github.com/rust-lang/crates.io-index" 1441 | dependencies = [ 1442 | "autocfg 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1443 | "rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1444 | ] 1445 | 1446 | [[package]] 1447 | name = "rand_chacha" 1448 | version = "0.2.0" 1449 | source = "registry+https://github.com/rust-lang/crates.io-index" 1450 | dependencies = [ 1451 | "autocfg 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1452 | "c2-chacha 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 1453 | "rand_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 1454 | ] 1455 | 1456 | [[package]] 1457 | name = "rand_core" 1458 | version = "0.3.1" 1459 | source = "registry+https://github.com/rust-lang/crates.io-index" 1460 | dependencies = [ 1461 | "rand_core 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1462 | ] 1463 | 1464 | [[package]] 1465 | name = "rand_core" 1466 | version = "0.4.0" 1467 | source = "registry+https://github.com/rust-lang/crates.io-index" 1468 | 1469 | [[package]] 1470 | name = "rand_core" 1471 | version = "0.5.0" 1472 | source = "registry+https://github.com/rust-lang/crates.io-index" 1473 | dependencies = [ 1474 | "getrandom 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 1475 | ] 1476 | 1477 | [[package]] 1478 | name = "rand_hc" 1479 | version = "0.1.0" 1480 | source = "registry+https://github.com/rust-lang/crates.io-index" 1481 | dependencies = [ 1482 | "rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1483 | ] 1484 | 1485 | [[package]] 1486 | name = "rand_hc" 1487 | version = "0.2.0" 1488 | source = "registry+https://github.com/rust-lang/crates.io-index" 1489 | dependencies = [ 1490 | "rand_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 1491 | ] 1492 | 1493 | [[package]] 1494 | name = "rand_isaac" 1495 | version = "0.1.1" 1496 | source = "registry+https://github.com/rust-lang/crates.io-index" 1497 | dependencies = [ 1498 | "rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1499 | ] 1500 | 1501 | [[package]] 1502 | name = "rand_jitter" 1503 | version = "0.1.4" 1504 | source = "registry+https://github.com/rust-lang/crates.io-index" 1505 | dependencies = [ 1506 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1507 | "rand_core 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1508 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1509 | ] 1510 | 1511 | [[package]] 1512 | name = "rand_os" 1513 | version = "0.1.3" 1514 | source = "registry+https://github.com/rust-lang/crates.io-index" 1515 | dependencies = [ 1516 | "cloudabi 0.0.3 (registry+https://github.com/rust-lang/crates.io-index)", 1517 | "fuchsia-cprng 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 1518 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1519 | "rand_core 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1520 | "rdrand 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1521 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1522 | ] 1523 | 1524 | [[package]] 1525 | name = "rand_pcg" 1526 | version = "0.1.2" 1527 | source = "registry+https://github.com/rust-lang/crates.io-index" 1528 | dependencies = [ 1529 | "autocfg 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1530 | "rand_core 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1531 | ] 1532 | 1533 | [[package]] 1534 | name = "rand_xorshift" 1535 | version = "0.1.1" 1536 | source = "registry+https://github.com/rust-lang/crates.io-index" 1537 | dependencies = [ 1538 | "rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1539 | ] 1540 | 1541 | [[package]] 1542 | name = "rdrand" 1543 | version = "0.4.0" 1544 | source = "registry+https://github.com/rust-lang/crates.io-index" 1545 | dependencies = [ 1546 | "rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1547 | ] 1548 | 1549 | [[package]] 1550 | name = "redox_syscall" 1551 | version = "0.1.56" 1552 | source = "registry+https://github.com/rust-lang/crates.io-index" 1553 | 1554 | [[package]] 1555 | name = "redox_users" 1556 | version = "0.3.0" 1557 | source = "registry+https://github.com/rust-lang/crates.io-index" 1558 | dependencies = [ 1559 | "argon2rs 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", 1560 | "failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 1561 | "rand_os 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 1562 | "redox_syscall 0.1.56 (registry+https://github.com/rust-lang/crates.io-index)", 1563 | ] 1564 | 1565 | [[package]] 1566 | name = "regex" 1567 | version = "1.1.9" 1568 | source = "registry+https://github.com/rust-lang/crates.io-index" 1569 | dependencies = [ 1570 | "aho-corasick 0.7.4 (registry+https://github.com/rust-lang/crates.io-index)", 1571 | "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 1572 | "regex-syntax 0.6.8 (registry+https://github.com/rust-lang/crates.io-index)", 1573 | "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", 1574 | "utf8-ranges 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)", 1575 | ] 1576 | 1577 | [[package]] 1578 | name = "regex-syntax" 1579 | version = "0.6.8" 1580 | source = "registry+https://github.com/rust-lang/crates.io-index" 1581 | dependencies = [ 1582 | "ucd-util 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 1583 | ] 1584 | 1585 | [[package]] 1586 | name = "resolv-conf" 1587 | version = "0.6.2" 1588 | source = "registry+https://github.com/rust-lang/crates.io-index" 1589 | dependencies = [ 1590 | "hostname 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 1591 | "quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 1592 | ] 1593 | 1594 | [[package]] 1595 | name = "rust-ini" 1596 | version = "0.13.0" 1597 | source = "registry+https://github.com/rust-lang/crates.io-index" 1598 | 1599 | [[package]] 1600 | name = "rustc-demangle" 1601 | version = "0.1.15" 1602 | source = "registry+https://github.com/rust-lang/crates.io-index" 1603 | 1604 | [[package]] 1605 | name = "rustc_version" 1606 | version = "0.2.3" 1607 | source = "registry+https://github.com/rust-lang/crates.io-index" 1608 | dependencies = [ 1609 | "semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)", 1610 | ] 1611 | 1612 | [[package]] 1613 | name = "ryu" 1614 | version = "1.0.0" 1615 | source = "registry+https://github.com/rust-lang/crates.io-index" 1616 | 1617 | [[package]] 1618 | name = "scoped_threadpool" 1619 | version = "0.1.9" 1620 | source = "registry+https://github.com/rust-lang/crates.io-index" 1621 | 1622 | [[package]] 1623 | name = "scopeguard" 1624 | version = "0.3.3" 1625 | source = "registry+https://github.com/rust-lang/crates.io-index" 1626 | 1627 | [[package]] 1628 | name = "scopeguard" 1629 | version = "1.0.0" 1630 | source = "registry+https://github.com/rust-lang/crates.io-index" 1631 | 1632 | [[package]] 1633 | name = "semver" 1634 | version = "0.9.0" 1635 | source = "registry+https://github.com/rust-lang/crates.io-index" 1636 | dependencies = [ 1637 | "semver-parser 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 1638 | ] 1639 | 1640 | [[package]] 1641 | name = "semver-parser" 1642 | version = "0.7.0" 1643 | source = "registry+https://github.com/rust-lang/crates.io-index" 1644 | 1645 | [[package]] 1646 | name = "serde" 1647 | version = "0.8.23" 1648 | source = "registry+https://github.com/rust-lang/crates.io-index" 1649 | 1650 | [[package]] 1651 | name = "serde" 1652 | version = "1.0.94" 1653 | source = "registry+https://github.com/rust-lang/crates.io-index" 1654 | dependencies = [ 1655 | "serde_derive 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 1656 | ] 1657 | 1658 | [[package]] 1659 | name = "serde-hjson" 1660 | version = "0.8.2" 1661 | source = "registry+https://github.com/rust-lang/crates.io-index" 1662 | dependencies = [ 1663 | "lazy_static 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", 1664 | "linked-hash-map 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 1665 | "num-traits 0.1.43 (registry+https://github.com/rust-lang/crates.io-index)", 1666 | "regex 1.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 1667 | "serde 0.8.23 (registry+https://github.com/rust-lang/crates.io-index)", 1668 | ] 1669 | 1670 | [[package]] 1671 | name = "serde_derive" 1672 | version = "1.0.94" 1673 | source = "registry+https://github.com/rust-lang/crates.io-index" 1674 | dependencies = [ 1675 | "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", 1676 | "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", 1677 | "syn 0.15.39 (registry+https://github.com/rust-lang/crates.io-index)", 1678 | ] 1679 | 1680 | [[package]] 1681 | name = "serde_json" 1682 | version = "1.0.40" 1683 | source = "registry+https://github.com/rust-lang/crates.io-index" 1684 | dependencies = [ 1685 | "itoa 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)", 1686 | "ryu 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", 1687 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 1688 | ] 1689 | 1690 | [[package]] 1691 | name = "serde_test" 1692 | version = "0.8.23" 1693 | source = "registry+https://github.com/rust-lang/crates.io-index" 1694 | dependencies = [ 1695 | "serde 0.8.23 (registry+https://github.com/rust-lang/crates.io-index)", 1696 | ] 1697 | 1698 | [[package]] 1699 | name = "serde_urlencoded" 1700 | version = "0.5.5" 1701 | source = "registry+https://github.com/rust-lang/crates.io-index" 1702 | dependencies = [ 1703 | "dtoa 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)", 1704 | "itoa 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)", 1705 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 1706 | "url 1.7.2 (registry+https://github.com/rust-lang/crates.io-index)", 1707 | ] 1708 | 1709 | [[package]] 1710 | name = "sha1" 1711 | version = "0.6.0" 1712 | source = "registry+https://github.com/rust-lang/crates.io-index" 1713 | 1714 | [[package]] 1715 | name = "sha2" 1716 | version = "0.8.0" 1717 | source = "registry+https://github.com/rust-lang/crates.io-index" 1718 | dependencies = [ 1719 | "block-buffer 0.7.3 (registry+https://github.com/rust-lang/crates.io-index)", 1720 | "digest 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)", 1721 | "fake-simd 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 1722 | "opaque-debug 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", 1723 | ] 1724 | 1725 | [[package]] 1726 | name = "signal-hook" 1727 | version = "0.1.9" 1728 | source = "registry+https://github.com/rust-lang/crates.io-index" 1729 | dependencies = [ 1730 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1731 | "signal-hook-registry 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", 1732 | ] 1733 | 1734 | [[package]] 1735 | name = "signal-hook-registry" 1736 | version = "1.0.1" 1737 | source = "registry+https://github.com/rust-lang/crates.io-index" 1738 | dependencies = [ 1739 | "arc-swap 0.3.11 (registry+https://github.com/rust-lang/crates.io-index)", 1740 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1741 | ] 1742 | 1743 | [[package]] 1744 | name = "siphasher" 1745 | version = "0.3.1" 1746 | source = "registry+https://github.com/rust-lang/crates.io-index" 1747 | 1748 | [[package]] 1749 | name = "slab" 1750 | version = "0.4.2" 1751 | source = "registry+https://github.com/rust-lang/crates.io-index" 1752 | 1753 | [[package]] 1754 | name = "slog" 1755 | version = "2.5.0" 1756 | source = "registry+https://github.com/rust-lang/crates.io-index" 1757 | 1758 | [[package]] 1759 | name = "slog-async" 1760 | version = "2.3.0" 1761 | source = "registry+https://github.com/rust-lang/crates.io-index" 1762 | dependencies = [ 1763 | "slog 2.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 1764 | "take_mut 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 1765 | "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", 1766 | ] 1767 | 1768 | [[package]] 1769 | name = "slog-term" 1770 | version = "2.4.1" 1771 | source = "registry+https://github.com/rust-lang/crates.io-index" 1772 | dependencies = [ 1773 | "atty 0.2.12 (registry+https://github.com/rust-lang/crates.io-index)", 1774 | "chrono 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 1775 | "slog 2.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 1776 | "term 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)", 1777 | "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", 1778 | ] 1779 | 1780 | [[package]] 1781 | name = "smallvec" 1782 | version = "0.6.10" 1783 | source = "registry+https://github.com/rust-lang/crates.io-index" 1784 | 1785 | [[package]] 1786 | name = "smallvec" 1787 | version = "1.1.0" 1788 | source = "registry+https://github.com/rust-lang/crates.io-index" 1789 | 1790 | [[package]] 1791 | name = "socket2" 1792 | version = "0.3.9" 1793 | source = "registry+https://github.com/rust-lang/crates.io-index" 1794 | dependencies = [ 1795 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 1796 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1797 | "redox_syscall 0.1.56 (registry+https://github.com/rust-lang/crates.io-index)", 1798 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1799 | ] 1800 | 1801 | [[package]] 1802 | name = "spin" 1803 | version = "0.5.0" 1804 | source = "registry+https://github.com/rust-lang/crates.io-index" 1805 | 1806 | [[package]] 1807 | name = "stable_deref_trait" 1808 | version = "1.1.1" 1809 | source = "registry+https://github.com/rust-lang/crates.io-index" 1810 | 1811 | [[package]] 1812 | name = "string" 1813 | version = "0.2.1" 1814 | source = "registry+https://github.com/rust-lang/crates.io-index" 1815 | dependencies = [ 1816 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 1817 | ] 1818 | 1819 | [[package]] 1820 | name = "stringprep" 1821 | version = "0.1.2" 1822 | source = "registry+https://github.com/rust-lang/crates.io-index" 1823 | dependencies = [ 1824 | "unicode-bidi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", 1825 | "unicode-normalization 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 1826 | ] 1827 | 1828 | [[package]] 1829 | name = "subtle" 1830 | version = "1.0.0" 1831 | source = "registry+https://github.com/rust-lang/crates.io-index" 1832 | 1833 | [[package]] 1834 | name = "syn" 1835 | version = "0.15.39" 1836 | source = "registry+https://github.com/rust-lang/crates.io-index" 1837 | dependencies = [ 1838 | "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", 1839 | "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", 1840 | "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1841 | ] 1842 | 1843 | [[package]] 1844 | name = "syn" 1845 | version = "1.0.14" 1846 | source = "registry+https://github.com/rust-lang/crates.io-index" 1847 | dependencies = [ 1848 | "proc-macro2 1.0.8 (registry+https://github.com/rust-lang/crates.io-index)", 1849 | "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 1850 | "unicode-xid 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1851 | ] 1852 | 1853 | [[package]] 1854 | name = "synstructure" 1855 | version = "0.10.2" 1856 | source = "registry+https://github.com/rust-lang/crates.io-index" 1857 | dependencies = [ 1858 | "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", 1859 | "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", 1860 | "syn 0.15.39 (registry+https://github.com/rust-lang/crates.io-index)", 1861 | "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1862 | ] 1863 | 1864 | [[package]] 1865 | name = "take_mut" 1866 | version = "0.2.2" 1867 | source = "registry+https://github.com/rust-lang/crates.io-index" 1868 | 1869 | [[package]] 1870 | name = "term" 1871 | version = "0.5.2" 1872 | source = "registry+https://github.com/rust-lang/crates.io-index" 1873 | dependencies = [ 1874 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 1875 | "dirs 1.0.5 (registry+https://github.com/rust-lang/crates.io-index)", 1876 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1877 | ] 1878 | 1879 | [[package]] 1880 | name = "thread_local" 1881 | version = "0.3.6" 1882 | source = "registry+https://github.com/rust-lang/crates.io-index" 1883 | dependencies = [ 1884 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 1885 | ] 1886 | 1887 | [[package]] 1888 | name = "threadpool" 1889 | version = "1.7.1" 1890 | source = "registry+https://github.com/rust-lang/crates.io-index" 1891 | dependencies = [ 1892 | "num_cpus 1.10.1 (registry+https://github.com/rust-lang/crates.io-index)", 1893 | ] 1894 | 1895 | [[package]] 1896 | name = "time" 1897 | version = "0.1.42" 1898 | source = "registry+https://github.com/rust-lang/crates.io-index" 1899 | dependencies = [ 1900 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1901 | "redox_syscall 0.1.56 (registry+https://github.com/rust-lang/crates.io-index)", 1902 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 1903 | ] 1904 | 1905 | [[package]] 1906 | name = "tokio" 1907 | version = "0.2.4" 1908 | source = "registry+https://github.com/rust-lang/crates.io-index" 1909 | dependencies = [ 1910 | "bytes 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)", 1911 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 1912 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 1913 | "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 1914 | "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)", 1915 | "mio-uds 0.6.7 (registry+https://github.com/rust-lang/crates.io-index)", 1916 | "pin-project-lite 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1917 | "slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 1918 | ] 1919 | 1920 | [[package]] 1921 | name = "tokio-codec" 1922 | version = "0.1.1" 1923 | source = "registry+https://github.com/rust-lang/crates.io-index" 1924 | dependencies = [ 1925 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 1926 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 1927 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 1928 | ] 1929 | 1930 | [[package]] 1931 | name = "tokio-current-thread" 1932 | version = "0.1.6" 1933 | source = "registry+https://github.com/rust-lang/crates.io-index" 1934 | dependencies = [ 1935 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 1936 | "tokio-executor 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 1937 | ] 1938 | 1939 | [[package]] 1940 | name = "tokio-executor" 1941 | version = "0.1.8" 1942 | source = "registry+https://github.com/rust-lang/crates.io-index" 1943 | dependencies = [ 1944 | "crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)", 1945 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 1946 | ] 1947 | 1948 | [[package]] 1949 | name = "tokio-io" 1950 | version = "0.1.12" 1951 | source = "registry+https://github.com/rust-lang/crates.io-index" 1952 | dependencies = [ 1953 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 1954 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 1955 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 1956 | ] 1957 | 1958 | [[package]] 1959 | name = "tokio-postgres" 1960 | version = "0.5.1" 1961 | source = "registry+https://github.com/rust-lang/crates.io-index" 1962 | dependencies = [ 1963 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 1964 | "bytes 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)", 1965 | "fallible-iterator 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1966 | "futures 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1967 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 1968 | "parking_lot 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)", 1969 | "percent-encoding 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1970 | "phf 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", 1971 | "pin-project-lite 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 1972 | "postgres-protocol 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 1973 | "postgres-types 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1974 | "tokio 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", 1975 | "tokio-util 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 1976 | ] 1977 | 1978 | [[package]] 1979 | name = "tokio-reactor" 1980 | version = "0.1.9" 1981 | source = "registry+https://github.com/rust-lang/crates.io-index" 1982 | dependencies = [ 1983 | "crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)", 1984 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 1985 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 1986 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 1987 | "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)", 1988 | "num_cpus 1.10.1 (registry+https://github.com/rust-lang/crates.io-index)", 1989 | "parking_lot 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)", 1990 | "slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 1991 | "tokio-executor 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 1992 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 1993 | "tokio-sync 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 1994 | ] 1995 | 1996 | [[package]] 1997 | name = "tokio-signal" 1998 | version = "0.2.7" 1999 | source = "registry+https://github.com/rust-lang/crates.io-index" 2000 | dependencies = [ 2001 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 2002 | "libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)", 2003 | "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)", 2004 | "mio-uds 0.6.7 (registry+https://github.com/rust-lang/crates.io-index)", 2005 | "signal-hook 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 2006 | "tokio-executor 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 2007 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 2008 | "tokio-reactor 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 2009 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 2010 | ] 2011 | 2012 | [[package]] 2013 | name = "tokio-sync" 2014 | version = "0.1.6" 2015 | source = "registry+https://github.com/rust-lang/crates.io-index" 2016 | dependencies = [ 2017 | "fnv 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)", 2018 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 2019 | ] 2020 | 2021 | [[package]] 2022 | name = "tokio-tcp" 2023 | version = "0.1.3" 2024 | source = "registry+https://github.com/rust-lang/crates.io-index" 2025 | dependencies = [ 2026 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 2027 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 2028 | "iovec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 2029 | "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)", 2030 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 2031 | "tokio-reactor 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 2032 | ] 2033 | 2034 | [[package]] 2035 | name = "tokio-timer" 2036 | version = "0.2.11" 2037 | source = "registry+https://github.com/rust-lang/crates.io-index" 2038 | dependencies = [ 2039 | "crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)", 2040 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 2041 | "slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", 2042 | "tokio-executor 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 2043 | ] 2044 | 2045 | [[package]] 2046 | name = "tokio-udp" 2047 | version = "0.1.3" 2048 | source = "registry+https://github.com/rust-lang/crates.io-index" 2049 | dependencies = [ 2050 | "bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)", 2051 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 2052 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 2053 | "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)", 2054 | "tokio-codec 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 2055 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 2056 | "tokio-reactor 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 2057 | ] 2058 | 2059 | [[package]] 2060 | name = "tokio-util" 2061 | version = "0.2.0" 2062 | source = "registry+https://github.com/rust-lang/crates.io-index" 2063 | dependencies = [ 2064 | "bytes 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)", 2065 | "futures-core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 2066 | "futures-sink 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 2067 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 2068 | "pin-project-lite 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)", 2069 | "tokio 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", 2070 | ] 2071 | 2072 | [[package]] 2073 | name = "toml" 2074 | version = "0.4.10" 2075 | source = "registry+https://github.com/rust-lang/crates.io-index" 2076 | dependencies = [ 2077 | "serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)", 2078 | ] 2079 | 2080 | [[package]] 2081 | name = "trust-dns-proto" 2082 | version = "0.7.4" 2083 | source = "registry+https://github.com/rust-lang/crates.io-index" 2084 | dependencies = [ 2085 | "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 2086 | "enum-as-inner 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 2087 | "failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 2088 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 2089 | "idna 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 2090 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 2091 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 2092 | "rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)", 2093 | "smallvec 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", 2094 | "socket2 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)", 2095 | "tokio-executor 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 2096 | "tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", 2097 | "tokio-reactor 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 2098 | "tokio-tcp 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 2099 | "tokio-timer 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", 2100 | "tokio-udp 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 2101 | "url 1.7.2 (registry+https://github.com/rust-lang/crates.io-index)", 2102 | ] 2103 | 2104 | [[package]] 2105 | name = "trust-dns-resolver" 2106 | version = "0.11.1" 2107 | source = "registry+https://github.com/rust-lang/crates.io-index" 2108 | dependencies = [ 2109 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 2110 | "failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 2111 | "futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)", 2112 | "ipconfig 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 2113 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 2114 | "log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", 2115 | "lru-cache 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", 2116 | "resolv-conf 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)", 2117 | "smallvec 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", 2118 | "tokio-executor 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 2119 | "trust-dns-proto 0.7.4 (registry+https://github.com/rust-lang/crates.io-index)", 2120 | ] 2121 | 2122 | [[package]] 2123 | name = "typenum" 2124 | version = "1.11.2" 2125 | source = "registry+https://github.com/rust-lang/crates.io-index" 2126 | 2127 | [[package]] 2128 | name = "ucd-util" 2129 | version = "0.1.3" 2130 | source = "registry+https://github.com/rust-lang/crates.io-index" 2131 | 2132 | [[package]] 2133 | name = "unicase" 2134 | version = "2.4.0" 2135 | source = "registry+https://github.com/rust-lang/crates.io-index" 2136 | dependencies = [ 2137 | "version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 2138 | ] 2139 | 2140 | [[package]] 2141 | name = "unicode-bidi" 2142 | version = "0.3.4" 2143 | source = "registry+https://github.com/rust-lang/crates.io-index" 2144 | dependencies = [ 2145 | "matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 2146 | ] 2147 | 2148 | [[package]] 2149 | name = "unicode-normalization" 2150 | version = "0.1.8" 2151 | source = "registry+https://github.com/rust-lang/crates.io-index" 2152 | dependencies = [ 2153 | "smallvec 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", 2154 | ] 2155 | 2156 | [[package]] 2157 | name = "unicode-xid" 2158 | version = "0.1.0" 2159 | source = "registry+https://github.com/rust-lang/crates.io-index" 2160 | 2161 | [[package]] 2162 | name = "unicode-xid" 2163 | version = "0.2.0" 2164 | source = "registry+https://github.com/rust-lang/crates.io-index" 2165 | 2166 | [[package]] 2167 | name = "url" 2168 | version = "1.7.2" 2169 | source = "registry+https://github.com/rust-lang/crates.io-index" 2170 | dependencies = [ 2171 | "encoding 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)", 2172 | "idna 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 2173 | "matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 2174 | "percent-encoding 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", 2175 | ] 2176 | 2177 | [[package]] 2178 | name = "utf8-ranges" 2179 | version = "1.0.3" 2180 | source = "registry+https://github.com/rust-lang/crates.io-index" 2181 | 2182 | [[package]] 2183 | name = "version_check" 2184 | version = "0.1.5" 2185 | source = "registry+https://github.com/rust-lang/crates.io-index" 2186 | 2187 | [[package]] 2188 | name = "widestring" 2189 | version = "0.4.0" 2190 | source = "registry+https://github.com/rust-lang/crates.io-index" 2191 | 2192 | [[package]] 2193 | name = "winapi" 2194 | version = "0.2.8" 2195 | source = "registry+https://github.com/rust-lang/crates.io-index" 2196 | 2197 | [[package]] 2198 | name = "winapi" 2199 | version = "0.3.7" 2200 | source = "registry+https://github.com/rust-lang/crates.io-index" 2201 | dependencies = [ 2202 | "winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 2203 | "winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 2204 | ] 2205 | 2206 | [[package]] 2207 | name = "winapi-build" 2208 | version = "0.1.1" 2209 | source = "registry+https://github.com/rust-lang/crates.io-index" 2210 | 2211 | [[package]] 2212 | name = "winapi-i686-pc-windows-gnu" 2213 | version = "0.4.0" 2214 | source = "registry+https://github.com/rust-lang/crates.io-index" 2215 | 2216 | [[package]] 2217 | name = "winapi-x86_64-pc-windows-gnu" 2218 | version = "0.4.0" 2219 | source = "registry+https://github.com/rust-lang/crates.io-index" 2220 | 2221 | [[package]] 2222 | name = "winreg" 2223 | version = "0.6.0" 2224 | source = "registry+https://github.com/rust-lang/crates.io-index" 2225 | dependencies = [ 2226 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 2227 | ] 2228 | 2229 | [[package]] 2230 | name = "winutil" 2231 | version = "0.1.1" 2232 | source = "registry+https://github.com/rust-lang/crates.io-index" 2233 | dependencies = [ 2234 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 2235 | ] 2236 | 2237 | [[package]] 2238 | name = "ws2_32-sys" 2239 | version = "0.2.1" 2240 | source = "registry+https://github.com/rust-lang/crates.io-index" 2241 | dependencies = [ 2242 | "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 2243 | "winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 2244 | ] 2245 | 2246 | [[package]] 2247 | name = "yaml-rust" 2248 | version = "0.4.3" 2249 | source = "registry+https://github.com/rust-lang/crates.io-index" 2250 | dependencies = [ 2251 | "linked-hash-map 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)", 2252 | ] 2253 | 2254 | [metadata] 2255 | "checksum actix-codec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9f2c11af4b06dc935d8e1b1491dad56bfb32febc49096a91e773f8535c176453" 2256 | "checksum actix-connect 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d7fbab0d79b2f3415a79570e3db12eaa75c26239541e613b832655145a5e9488" 2257 | "checksum actix-http 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)" = "29c11d33772c790e9aeb2e024834bc084f7496598482908e2424efd768c912b6" 2258 | "checksum actix-router 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "23224bb527e204261d0291102cb9b52713084def67d94f7874923baefe04ccf7" 2259 | "checksum actix-rt 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "61e09627004cb25149fd177c4a062d2061c4ec40aae5820ecd37a87195e759f8" 2260 | "checksum actix-server 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "ba8c936356c882420eab87051b12ca1926dc42348863d05fff7eb151df9cddbb" 2261 | "checksum actix-server-config 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "e78703f07d0bd08b426b482d53569d84f1e1929024f0431b3a5a2dc0c1c60e0f" 2262 | "checksum actix-service 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)" = "aaecc01bbc595ebd7a563a7d4f8a607d0b964bb55273c6f362b0b02c26508cf2" 2263 | "checksum actix-threadpool 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "1c29f7c554d56b3841f4bb85d5b3dee01ba536e1307679f56eb54de28aaec3fb" 2264 | "checksum actix-utils 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "b307201d074c963041cd8858d6b6a82ca23369827d613da5d6e972de123d3c14" 2265 | "checksum actix-web 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)" = "d0dc7ab62d04b9eeb0f368ad9c6ee20c2e3541fb9a25a5eb727c9118b59e8ff2" 2266 | "checksum actix-web-codegen 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "3fe9e3cdec1e645b675f354766e0688c5705021c85ab3cf739be1c8999b91c76" 2267 | "checksum adler32 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)" = "7e522997b529f05601e05166c07ed17789691f562762c7f3b987263d2dedee5c" 2268 | "checksum aho-corasick 0.7.4 (registry+https://github.com/rust-lang/crates.io-index)" = "36b7aa1ccb7d7ea3f437cf025a2ab1c47cc6c1bc9fc84918ff449def12f5e282" 2269 | "checksum arc-swap 0.3.11 (registry+https://github.com/rust-lang/crates.io-index)" = "bc4662175ead9cd84451d5c35070517777949a2ed84551764129cedb88384841" 2270 | "checksum argon2rs 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)" = "3f67b0b6a86dae6e67ff4ca2b6201396074996379fba2b92ff649126f37cb392" 2271 | "checksum arrayvec 0.4.11 (registry+https://github.com/rust-lang/crates.io-index)" = "b8d73f9beda665eaa98ab9e4f7442bd4e7de6652587de55b2525e52e29c1b0ba" 2272 | "checksum atty 0.2.12 (registry+https://github.com/rust-lang/crates.io-index)" = "ecaaea69f52b3b18633611ec0007d188517d0366f47ff703d400fa6879d6f8d5" 2273 | "checksum autocfg 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "0e49efa51329a5fd37e7c79db4621af617cd4e3e5bc224939808d076077077bf" 2274 | "checksum awc 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "4c4763e6aa29a801d761dc3464f081d439ea5249ba90c3c3bdfc8dd3f739d233" 2275 | "checksum backtrace 0.3.32 (registry+https://github.com/rust-lang/crates.io-index)" = "18b50f5258d1a9ad8396d2d345827875de4261b158124d4c819d9b351454fae5" 2276 | "checksum backtrace-sys 0.1.30 (registry+https://github.com/rust-lang/crates.io-index)" = "5b3a000b9c543553af61bc01cbfc403b04b5caa9e421033866f2e98061eb3e61" 2277 | "checksum base64 0.10.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0b25d992356d2eb0ed82172f5248873db5560c4721f564b13cb5193bda5e668e" 2278 | "checksum base64 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b41b7ea54a0c9d92199de89e20e58d49f02f8e699814ef3fdf266f6f748d15c7" 2279 | "checksum bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3d155346769a6855b86399e9bc3814ab343cd3d62c7e985113d46a0ec3c281fd" 2280 | "checksum blake2-rfc 0.2.18 (registry+https://github.com/rust-lang/crates.io-index)" = "5d6d530bdd2d52966a6d03b7a964add7ae1a288d25214066fd4b600f0f796400" 2281 | "checksum block-buffer 0.7.3 (registry+https://github.com/rust-lang/crates.io-index)" = "c0940dc441f31689269e10ac70eb1002a3a1d3ad1390e030043662eb7fe4688b" 2282 | "checksum block-padding 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "6d4dc3af3ee2e12f3e5d224e5e1e3d73668abbeb69e566d361f7d5563a4fdf09" 2283 | "checksum brotli-sys 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "4445dea95f4c2b41cde57cc9fee236ae4dbae88d8fcbdb4750fc1bb5d86aaecd" 2284 | "checksum brotli2 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "0cb036c3eade309815c15ddbacec5b22c4d1f3983a774ab2eac2e3e9ea85568e" 2285 | "checksum byte-tools 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "e3b5ca7a04898ad4bcd41c90c5285445ff5b791899bb1b0abdd2a2aa791211d7" 2286 | "checksum byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "a7c3dd8985a7111efc5c80b44e23ecdd8c007de8ade3b96595387e812b957cf5" 2287 | "checksum bytes 0.4.12 (registry+https://github.com/rust-lang/crates.io-index)" = "206fdffcfa2df7cbe15601ef46c813fce0965eb3286db6b56c583b814b51c81c" 2288 | "checksum bytes 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)" = "130aac562c0dd69c56b3b1cc8ffd2e17be31d0b6c25b61c96b76231aa23e39e1" 2289 | "checksum c2-chacha 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7d64d04786e0f528460fc884753cf8dddcc466be308f6026f8e355c41a0e4101" 2290 | "checksum cc 1.0.37 (registry+https://github.com/rust-lang/crates.io-index)" = "39f75544d7bbaf57560d2168f28fd649ff9c76153874db88bdbdfd839b1a7e7d" 2291 | "checksum cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "b486ce3ccf7ffd79fdeb678eac06a9e6c09fc88d33836340becb8fffe87c5e33" 2292 | "checksum chrono 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)" = "77d81f58b7301084de3b958691458a53c3f7e0b1d702f77e550b6a88e3a88abe" 2293 | "checksum cloudabi 0.0.3 (registry+https://github.com/rust-lang/crates.io-index)" = "ddfc5b9aa5d4507acaf872de71051dfd0e309860e88966e1051e462a077aac4f" 2294 | "checksum config 0.9.3 (registry+https://github.com/rust-lang/crates.io-index)" = "f9107d78ed62b3fa5a86e7d18e647abed48cfd8f8fab6c72f4cdb982d196f7e6" 2295 | "checksum constant_time_eq 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "8ff012e225ce166d4422e0e78419d901719760f62ae2b7969ca6b564d1b54a9e" 2296 | "checksum copyless 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "6ff9c56c9fb2a49c05ef0e431485a22400af20d33226dc0764d891d09e724127" 2297 | "checksum crc32fast 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ba125de2af0df55319f41944744ad91c71113bf74a4646efff39afe1f6842db1" 2298 | "checksum crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)" = "f8306fcef4a7b563b76b7dd949ca48f52bc1141aa067d2ea09565f3e2652aa5c" 2299 | "checksum crypto-mac 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "4434400df11d95d556bac068ddfedd482915eb18fe8bea89bc80b6e4b1c179e5" 2300 | "checksum derive_more 0.14.1 (registry+https://github.com/rust-lang/crates.io-index)" = "6d944ac6003ed268757ef1ee686753b57efc5fcf0ebe7b64c9fc81e7e32ff839" 2301 | "checksum derive_more 0.15.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7a141330240c921ec6d074a3e188a7c7ef95668bb95e7d44fa0e5778ec2a7afe" 2302 | "checksum digest 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)" = "f3d0c8c8752312f9713efd397ff63acb9f85585afbf179282e720e7704954dd5" 2303 | "checksum dirs 1.0.5 (registry+https://github.com/rust-lang/crates.io-index)" = "3fd78930633bd1c6e35c4b42b1df7b0cbc6bc191146e512bb3bedf243fcc3901" 2304 | "checksum dirs 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "1c4ef5a8b902d393339e2a2c7fe573af92ce7e0ee5a3ff827b4c9ad7e07e4fa1" 2305 | "checksum dirs-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "937756392ec77d1f2dd9dc3ac9d69867d109a2121479d72c364e42f4cab21e2d" 2306 | "checksum dtoa 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)" = "ea57b42383d091c85abcc2706240b94ab2a8fa1fc81c10ff23c4de06e2a90b5e" 2307 | "checksum either 1.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "5527cfe0d098f36e3f8839852688e63c8fff1c90b2b405aef730615f9a7bcf7b" 2308 | "checksum encoding 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)" = "6b0d943856b990d12d3b55b359144ff341533e516d94098b1d3fc1ac666d36ec" 2309 | "checksum encoding-index-japanese 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)" = "04e8b2ff42e9a05335dbf8b5c6f7567e5591d0d916ccef4e0b1710d32a0d0c91" 2310 | "checksum encoding-index-korean 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)" = "4dc33fb8e6bcba213fe2f14275f0963fd16f0a02c878e3095ecfdf5bee529d81" 2311 | "checksum encoding-index-simpchinese 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)" = "d87a7194909b9118fc707194baa434a4e3b0fb6a5a757c73c3adb07aa25031f7" 2312 | "checksum encoding-index-singlebyte 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)" = "3351d5acffb224af9ca265f435b859c7c01537c0849754d3db3fdf2bfe2ae84a" 2313 | "checksum encoding-index-tradchinese 1.20141219.5 (registry+https://github.com/rust-lang/crates.io-index)" = "fd0e20d5688ce3cab59eb3ef3a2083a5c77bf496cb798dc6fcdb75f323890c18" 2314 | "checksum encoding_index_tests 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "a246d82be1c9d791c5dfde9a2bd045fc3cbba3fa2b11ad558f27d01712f00569" 2315 | "checksum encoding_rs 0.8.17 (registry+https://github.com/rust-lang/crates.io-index)" = "4155785c79f2f6701f185eb2e6b4caf0555ec03477cb4c70db67b465311620ed" 2316 | "checksum enum-as-inner 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "3d58266c97445680766be408285e798d3401c6d4c378ec5552e78737e681e37d" 2317 | "checksum failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "795bd83d3abeb9220f257e597aa0080a508b27533824adf336529648f6abf7e2" 2318 | "checksum failure_derive 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "ea1063915fd7ef4309e222a5a07cf9c319fb9c7836b1f89b85458672dbb127e1" 2319 | "checksum fake-simd 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e88a8acf291dafb59c2d96e8f59828f3838bb1a70398823ade51a84de6a6deed" 2320 | "checksum fallible-iterator 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "4443176a9f2c162692bd3d352d745ef9413eec5782a80d8fd6f8a1ac692a07f7" 2321 | "checksum flate2 1.0.9 (registry+https://github.com/rust-lang/crates.io-index)" = "550934ad4808d5d39365e5d61727309bf18b3b02c6c56b729cb92e7dd84bc3d8" 2322 | "checksum fnv 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)" = "2fad85553e09a6f881f739c29f0b00b0f01357c743266d478b68951ce23285f3" 2323 | "checksum fuchsia-cprng 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "a06f77d526c1a601b7c4cdd98f54b5eaabffc14d5f2f0296febdc7f357c6d3ba" 2324 | "checksum fuchsia-zircon 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82" 2325 | "checksum fuchsia-zircon-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7" 2326 | "checksum futures 0.1.28 (registry+https://github.com/rust-lang/crates.io-index)" = "45dc39533a6cae6da2b56da48edae506bb767ec07370f86f70fc062e9d435869" 2327 | "checksum futures 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b6f16056ecbb57525ff698bb955162d0cd03bee84e6241c27ff75c08d8ca5987" 2328 | "checksum futures-channel 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "fcae98ca17d102fd8a3603727b9259fcf7fa4239b603d2142926189bc8999b86" 2329 | "checksum futures-core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "79564c427afefab1dfb3298535b21eda083ef7935b4f0ecbfcb121f0aec10866" 2330 | "checksum futures-executor 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "1e274736563f686a837a0568b478bdabfeaec2dca794b5649b04e2fe1627c231" 2331 | "checksum futures-io 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "e676577d229e70952ab25f3945795ba5b16d63ca794ca9d2c860e5595d20b5ff" 2332 | "checksum futures-macro 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "52e7c56c15537adb4f76d0b7a76ad131cb4d2f4f32d3b0bcabcbe1c7c5e87764" 2333 | "checksum futures-sink 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "171be33efae63c2d59e6dbba34186fe0d6394fb378069a76dfd80fdcffd43c16" 2334 | "checksum futures-task 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0bae52d6b29cf440e298856fec3965ee6fa71b06aa7495178615953fd669e5f9" 2335 | "checksum futures-util 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "c0d66274fb76985d3c62c886d1da7ac4c0903a8c9f754e8fe0f35a6a6cc39e76" 2336 | "checksum generic-array 0.12.3 (registry+https://github.com/rust-lang/crates.io-index)" = "c68f0274ae0e023facc3c97b2e00f076be70e254bc851d972503b328db79b2ec" 2337 | "checksum generic-array 0.13.2 (registry+https://github.com/rust-lang/crates.io-index)" = "0ed1e761351b56f54eb9dcd0cfaca9fd0daecf93918e1cfc01c8a3d26ee7adcd" 2338 | "checksum getrandom 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "e65cce4e5084b14874c4e7097f38cab54f47ee554f9194673456ea379dcc4c55" 2339 | "checksum h2 0.1.25 (registry+https://github.com/rust-lang/crates.io-index)" = "a539b63339fbbb00e081e84b6e11bd1d9634a82d91da2984a18ac74a8823f392" 2340 | "checksum hashbrown 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "e1de41fb8dba9714efd92241565cdff73f78508c95697dd56787d3cba27e2353" 2341 | "checksum hmac 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)" = "5dcb5e64cda4c23119ab41ba960d1e170a774c8e4b9d9e6a9bc18aabf5e59695" 2342 | "checksum hostname 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "21ceb46a83a85e824ef93669c8b390009623863b5c195d1ba747292c0c72f94e" 2343 | "checksum http 0.1.17 (registry+https://github.com/rust-lang/crates.io-index)" = "eed324f0f0daf6ec10c474f150505af2c143f251722bf9dbd1261bd1f2ee2c1a" 2344 | "checksum httparse 1.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "cd179ae861f0c2e53da70d892f5f3029f9594be0c41dc5269cd371691b1dc2f9" 2345 | "checksum idna 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "38f09e0f0b1fb55fdee1f17470ad800da77af5186a1a76c026b679358b7e844e" 2346 | "checksum indexmap 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7e81a7c05f79578dbc15793d8b619db9ba32b4577003ef3af1a91c416798c58d" 2347 | "checksum iovec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "dbe6e417e7d0975db6512b90796e8ce223145ac4e33c377e4a42882a0e88bb08" 2348 | "checksum ipconfig 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "aa79fa216fbe60834a9c0737d7fcd30425b32d1c58854663e24d4c4b328ed83f" 2349 | "checksum itoa 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)" = "501266b7edd0174f8530248f87f99c88fbe60ca4ef3dd486835b8d8d53136f7f" 2350 | "checksum kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d" 2351 | "checksum language-tags 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "a91d884b6667cd606bb5a69aa0c99ba811a115fc68915e7056ec08a46e93199a" 2352 | "checksum lazy_static 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "76f033c7ad61445c5b347c7382dd1237847eb1bce590fe50365dcb33d546be73" 2353 | "checksum lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "bc5729f27f159ddd61f4df6228e827e86643d4d3e7c32183cb30a1c08f604a14" 2354 | "checksum libc 0.2.59 (registry+https://github.com/rust-lang/crates.io-index)" = "3262021842bf00fe07dbd6cf34ff25c99d7a7ebef8deea84db72be3ea3bb0aff" 2355 | "checksum linked-hash-map 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "6d262045c5b87c0861b3f004610afd0e2c851e2908d08b6c870cbb9d5f494ecd" 2356 | "checksum linked-hash-map 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "ae91b68aebc4ddb91978b11a1b02ddd8602a05ec19002801c5666000e05e0f83" 2357 | "checksum lock_api 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "62ebf1391f6acad60e5c8b43706dde4582df75c06698ab44511d15016bc2442c" 2358 | "checksum lock_api 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ed946d4529956a20f2d63ebe1b69996d5a2137c91913fe3ebbeff957f5bca7ff" 2359 | "checksum lock_api 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "79b2de95ecb4691949fea4716ca53cdbcfccb2c612e19644a8bad05edcf9f47b" 2360 | "checksum log 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)" = "c275b6ad54070ac2d665eef9197db647b32239c9d244bfb6f041a766d00da5b3" 2361 | "checksum lru-cache 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "31e24f1ad8321ca0e8a1e0ac13f23cb668e6f5466c2c57319f6a5cf1cc8e3b1c" 2362 | "checksum matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "7ffc5c5338469d4d3ea17d269fa8ea3512ad247247c30bd2df69e68309ed0a08" 2363 | "checksum md5 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "490cc448043f947bae3cbee9c203358d62dbee0db12107a74be5c30ccfd09771" 2364 | "checksum memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "88579771288728879b57485cc7d6b07d648c9f0141eb955f8ab7f9d45394468e" 2365 | "checksum mime 0.3.13 (registry+https://github.com/rust-lang/crates.io-index)" = "3e27ca21f40a310bd06d9031785f4801710d566c184a6e15bad4f1d9b65f9425" 2366 | "checksum miniz-sys 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)" = "1e9e3ae51cea1576ceba0dde3d484d30e6e5b86dee0b2d412fe3a16a15c98202" 2367 | "checksum miniz_oxide 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "b6c3756d66cf286314d5f7ebe74886188a9a92f5eee68b06f31ac2b4f314c99d" 2368 | "checksum miniz_oxide_c_api 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "5b78ca5446dd9fe0dab00e058731b6b08a8c1d2b9cdb8efb10876e24e9ae2494" 2369 | "checksum mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)" = "302dec22bcf6bae6dfb69c647187f4b4d0fb6f535521f7bc022430ce8e12008f" 2370 | "checksum mio-uds 0.6.7 (registry+https://github.com/rust-lang/crates.io-index)" = "966257a94e196b11bb43aca423754d87429960a768de9414f3691d6957abf125" 2371 | "checksum miow 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "8c1f2f3b1cf331de6896aabf6e9d55dca90356cc9960cca7eaaf408a355ae919" 2372 | "checksum nanoid 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ef553a0f07a7a45c731f0c5d83cf9ef9caddf7407e413142731db416504bfe0f" 2373 | "checksum net2 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)" = "42550d9fb7b6684a6d404d9fa7250c2eb2646df731d1c06afc06dcee9e1bcf88" 2374 | "checksum nodrop 0.1.13 (registry+https://github.com/rust-lang/crates.io-index)" = "2f9667ddcc6cc8a43afc9b7917599d7216aa09c463919ea32c59ed6cac8bc945" 2375 | "checksum nom 4.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "2ad2a91a8e869eeb30b9cb3119ae87773a8f4ae617f41b1eb9c154b2905f7bd6" 2376 | "checksum num-integer 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)" = "b85e541ef8255f6cf42bbfe4ef361305c6c135d10919ecc26126c4e5ae94bc09" 2377 | "checksum num-traits 0.1.43 (registry+https://github.com/rust-lang/crates.io-index)" = "92e5113e9fd4cc14ded8e499429f396a20f98c772a47cc8622a736e1ec843c31" 2378 | "checksum num-traits 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "6ba9a427cfca2be13aa6f6403b0b7e7368fe982bfa16fccc450ce74c46cd9b32" 2379 | "checksum num_cpus 1.10.1 (registry+https://github.com/rust-lang/crates.io-index)" = "bcef43580c035376c0705c42792c294b66974abbfd2789b511784023f71f3273" 2380 | "checksum opaque-debug 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "2839e79665f131bdb5782e51f2c6c9599c133c6098982a54c794358bf432529c" 2381 | "checksum owning_ref 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "49a4b8ea2179e6a2e27411d3bca09ca6dd630821cf6894c6c7c8467a8ee7ef13" 2382 | "checksum parking_lot 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "92e98c49ab0b7ce5b222f2cc9193fc4efe11c6d0bd4f648e374684a6857b1cfc" 2383 | "checksum parking_lot 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)" = "ab41b4aed082705d1056416ae4468b6ea99d52599ecf3169b00088d43113e337" 2384 | "checksum parking_lot 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fa7767817701cce701d5585b9c4db3cdd02086398322c1d7e8bf5094a96a2ce7" 2385 | "checksum parking_lot_core 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "94c8c7923936b28d546dfd14d4472eaf34c99b14e1c973a32b3e6d4eb04298c9" 2386 | "checksum parking_lot_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "cb88cb1cb3790baa6776844f968fea3be44956cf184fa1be5a03341f5491278c" 2387 | "checksum parking_lot_core 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7582838484df45743c8434fbff785e8edf260c28748353d44bc0da32e0ceabf1" 2388 | "checksum percent-encoding 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "31010dd2e1ac33d5b46a5b413495239882813e0369f8ed8a5e266f173602f831" 2389 | "checksum percent-encoding 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d4fd5641d01c8f18a23da7b6fe29298ff4b55afcccdf78973b24cf3175fee32e" 2390 | "checksum phf 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3dfb61232e34fcb633f43d12c58f83c1df82962dcdfa565a4e866ffc17dafe12" 2391 | "checksum phf_shared 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "c00cf8b9eafe68dde5e9eaa2cef8ee84a9336a47d566ec55ca16589633b65af7" 2392 | "checksum pin-project-lite 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "237844750cfbb86f67afe27eee600dfbbcb6188d734139b534cbfbf4f96792ae" 2393 | "checksum pin-utils 0.1.0-alpha.4 (registry+https://github.com/rust-lang/crates.io-index)" = "5894c618ce612a3fa23881b152b608bafb8c56cfc22f434a3ba3120b40f7b587" 2394 | "checksum postgres 0.17.0 (registry+https://github.com/rust-lang/crates.io-index)" = "96dd5c8eddec65a5497798ebde2e5c74a93ef8b66782c1b09eeab9bb8538aebc" 2395 | "checksum postgres-derive 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "c857dd221cb0e7d8414b894a0ce29eae44d453dda0baa132447878e75e701477" 2396 | "checksum postgres-protocol 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "a30f0e172ae0fb0653dbf777ad10a74b8e58d6de95a892f2e1d3e94a9df9a844" 2397 | "checksum postgres-types 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "eab1dd99401779ab03bc3872f196fb02c420e76f416c850be494a6f2d67287ad" 2398 | "checksum ppv-lite86 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)" = "e3cbf9f658cdb5000fcf6f362b8ea2ba154b9f146a61c7a20d647034c6b6561b" 2399 | "checksum proc-macro-hack 0.5.11 (registry+https://github.com/rust-lang/crates.io-index)" = "ecd45702f76d6d3c75a80564378ae228a85f0b59d2f3ed43c91b4a69eb2ebfc5" 2400 | "checksum proc-macro-nested 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "369a6ed065f249a159e06c45752c780bda2fb53c995718f9e484d08daa9eb42e" 2401 | "checksum proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)" = "cf3d2011ab5c909338f7887f4fc896d35932e29146c12c8d01da6b22a80ba759" 2402 | "checksum proc-macro2 1.0.8 (registry+https://github.com/rust-lang/crates.io-index)" = "3acb317c6ff86a4e579dfa00fc5e6cca91ecbb4e7eb2df0468805b674eb88548" 2403 | "checksum quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9274b940887ce9addde99c4eee6b5c44cc494b182b97e73dc8ffdcb3397fd3f0" 2404 | "checksum quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)" = "6ce23b6b870e8f94f81fb0a363d65d86675884b34a09043c81e5562f11c1f8e1" 2405 | "checksum quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "053a8c8bcc71fcce321828dc897a98ab9760bef03a4fc36693c231e5b3216cfe" 2406 | "checksum rand 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)" = "552840b97013b1a26992c11eac34bdd778e464601a4c2054b5f0bff7c6761293" 2407 | "checksum rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)" = "6d71dacdc3c88c1fde3885a3be3fbab9f35724e6ce99467f7d9c5026132184ca" 2408 | "checksum rand 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d47eab0e83d9693d40f825f86948aa16eff6750ead4bdffc4ab95b8b3a7f052c" 2409 | "checksum rand_chacha 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "556d3a1ca6600bfcbab7c7c91ccb085ac7fbbcd70e008a98742e7847f4f7bcef" 2410 | "checksum rand_chacha 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "e193067942ef6f485a349a113329140d0ab9e2168ce92274499bb0e9a4190d9d" 2411 | "checksum rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7a6fdeb83b075e8266dcc8762c22776f6877a63111121f5f8c7411e5be7eed4b" 2412 | "checksum rand_core 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d0e7a549d590831370895ab7ba4ea0c1b6b011d106b5ff2da6eee112615e6dc0" 2413 | "checksum rand_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "615e683324e75af5d43d8f7a39ffe3ee4a9dc42c5c701167a71dc59c3a493aca" 2414 | "checksum rand_hc 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7b40677c7be09ae76218dc623efbf7b18e34bced3f38883af07bb75630a21bc4" 2415 | "checksum rand_hc 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ca3129af7b92a17112d59ad498c6f81eaf463253766b90396d39ea7a39d6613c" 2416 | "checksum rand_isaac 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "ded997c9d5f13925be2a6fd7e66bf1872597f759fd9dd93513dd7e92e5a5ee08" 2417 | "checksum rand_jitter 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "1166d5c91dc97b88d1decc3285bb0a99ed84b05cfd0bc2341bdf2d43fc41e39b" 2418 | "checksum rand_os 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "7b75f676a1e053fc562eafbb47838d67c84801e38fc1ba459e8f180deabd5071" 2419 | "checksum rand_pcg 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "abf9b09b01790cfe0364f52bf32995ea3c39f4d2dd011eac241d2914146d0b44" 2420 | "checksum rand_xorshift 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "cbf7e9e623549b0e21f6e97cf8ecf247c1a8fd2e8a992ae265314300b2455d5c" 2421 | "checksum rdrand 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "678054eb77286b51581ba43620cc911abf02758c91f93f479767aed0f90458b2" 2422 | "checksum redox_syscall 0.1.56 (registry+https://github.com/rust-lang/crates.io-index)" = "2439c63f3f6139d1b57529d16bc3b8bb855230c8efcc5d3a896c8bea7c3b1e84" 2423 | "checksum redox_users 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3fe5204c3a17e97dde73f285d49be585df59ed84b50a872baf416e73b62c3828" 2424 | "checksum regex 1.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "d9d8297cc20bbb6184f8b45ff61c8ee6a9ac56c156cec8e38c3e5084773c44ad" 2425 | "checksum regex-syntax 0.6.8 (registry+https://github.com/rust-lang/crates.io-index)" = "9b01330cce219c1c6b2e209e5ed64ccd587ae5c67bed91c0b49eecf02ae40e21" 2426 | "checksum resolv-conf 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)" = "b263b4aa1b5de9ffc0054a2386f96992058bb6870aab516f8cdeb8a667d56dcb" 2427 | "checksum rust-ini 0.13.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3e52c148ef37f8c375d49d5a73aa70713125b7f19095948a923f80afdeb22ec2" 2428 | "checksum rustc-demangle 0.1.15 (registry+https://github.com/rust-lang/crates.io-index)" = "a7f4dccf6f4891ebcc0c39f9b6eb1a83b9bf5d747cb439ec6fba4f3b977038af" 2429 | "checksum rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a" 2430 | "checksum ryu 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "c92464b447c0ee8c4fb3824ecc8383b81717b9f1e74ba2e72540aef7b9f82997" 2431 | "checksum scoped_threadpool 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "1d51f5df5af43ab3f1360b429fa5e0152ac5ce8c0bd6485cae490332e96846a8" 2432 | "checksum scopeguard 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "94258f53601af11e6a49f722422f6e3425c52b06245a5cf9bc09908b174f5e27" 2433 | "checksum scopeguard 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b42e15e59b18a828bbf5c58ea01debb36b9b096346de35d941dcb89009f24a0d" 2434 | "checksum semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1d7eb9ef2c18661902cc47e535f9bc51b78acd254da71d375c2f6720d9a40403" 2435 | "checksum semver-parser 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" 2436 | "checksum serde 0.8.23 (registry+https://github.com/rust-lang/crates.io-index)" = "9dad3f759919b92c3068c696c15c3d17238234498bbdcc80f2c469606f948ac8" 2437 | "checksum serde 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)" = "076a696fdea89c19d3baed462576b8f6d663064414b5c793642da8dfeb99475b" 2438 | "checksum serde-hjson 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)" = "0b833c5ad67d52ced5f5938b2980f32a9c1c5ef047f0b4fb3127e7a423c76153" 2439 | "checksum serde_derive 1.0.94 (registry+https://github.com/rust-lang/crates.io-index)" = "ef45eb79d6463b22f5f9e16d283798b7c0175ba6050bc25c1a946c122727fe7b" 2440 | "checksum serde_json 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)" = "051c49229f282f7c6f3813f8286cc1e3323e8051823fce42c7ea80fe13521704" 2441 | "checksum serde_test 0.8.23 (registry+https://github.com/rust-lang/crates.io-index)" = "110b3dbdf8607ec493c22d5d947753282f3bae73c0f56d322af1e8c78e4c23d5" 2442 | "checksum serde_urlencoded 0.5.5 (registry+https://github.com/rust-lang/crates.io-index)" = "642dd69105886af2efd227f75a520ec9b44a820d65bc133a9131f7d229fd165a" 2443 | "checksum sha1 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)" = "2579985fda508104f7587689507983eadd6a6e84dd35d6d115361f530916fa0d" 2444 | "checksum sha2 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7b4d8bfd0e469f417657573d8451fb33d16cfe0989359b93baf3a1ffc639543d" 2445 | "checksum signal-hook 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "72ab58f1fda436857e6337dcb6a5aaa34f16c5ddc87b3a8b6ef7a212f90b9c5a" 2446 | "checksum signal-hook-registry 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "cded4ffa32146722ec54ab1f16320568465aa922aa9ab4708129599740da85d7" 2447 | "checksum siphasher 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "83da420ee8d1a89e640d0948c646c1c088758d3a3c538f943bfa97bdac17929d" 2448 | "checksum slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "c111b5bd5695e56cffe5129854aa230b39c93a305372fdbb2668ca2394eea9f8" 2449 | "checksum slog 2.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "36d9e85f8df625a6ac087188d0826546df56e07190bede661c10c95a95890cad" 2450 | "checksum slog-async 2.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "e544d16c6b230d84c866662fe55e31aacfca6ae71e6fc49ae9a311cb379bfc2f" 2451 | "checksum slog-term 2.4.1 (registry+https://github.com/rust-lang/crates.io-index)" = "cb9b3fd9a3c2c86580fce3558a98ed7c69039da0288b08a3f15b371635254e08" 2452 | "checksum smallvec 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)" = "ab606a9c5e214920bb66c458cd7be8ef094f813f20fe77a54cc7dbfff220d4b7" 2453 | "checksum smallvec 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "44e59e0c9fa00817912ae6e4e6e3c4fe04455e75699d06eedc7d85917ed8e8f4" 2454 | "checksum socket2 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)" = "4e626972d3593207547f14bf5fc9efa4d0e7283deb73fef1dff313dae9ab8878" 2455 | "checksum spin 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "44363f6f51401c34e7be73db0db371c04705d35efbe9f7d6082e03a921a32c55" 2456 | "checksum stable_deref_trait 1.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "dba1a27d3efae4351c8051072d619e3ade2820635c3958d826bfea39d59b54c8" 2457 | "checksum string 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "d24114bfcceb867ca7f71a0d3fe45d45619ec47a6fbfa98cb14e14250bfa5d6d" 2458 | "checksum stringprep 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "8ee348cb74b87454fff4b551cbf727025810a004f88aeacae7f85b87f4e9a1c1" 2459 | "checksum subtle 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "2d67a5a62ba6e01cb2192ff309324cb4875d0c451d55fe2319433abe7a05a8ee" 2460 | "checksum syn 0.15.39 (registry+https://github.com/rust-lang/crates.io-index)" = "b4d960b829a55e56db167e861ddb43602c003c7be0bee1d345021703fac2fb7c" 2461 | "checksum syn 1.0.14 (registry+https://github.com/rust-lang/crates.io-index)" = "af6f3550d8dff9ef7dc34d384ac6f107e5d31c8f57d9f28e0081503f547ac8f5" 2462 | "checksum synstructure 0.10.2 (registry+https://github.com/rust-lang/crates.io-index)" = "02353edf96d6e4dc81aea2d8490a7e9db177bf8acb0e951c24940bf866cb313f" 2463 | "checksum take_mut 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "f764005d11ee5f36500a149ace24e00e3da98b0158b3e2d53a7495660d3f4d60" 2464 | "checksum term 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "edd106a334b7657c10b7c540a0106114feadeb4dc314513e97df481d5d966f42" 2465 | "checksum thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)" = "c6b53e329000edc2b34dbe8545fd20e55a333362d0a321909685a19bd28c3f1b" 2466 | "checksum threadpool 1.7.1 (registry+https://github.com/rust-lang/crates.io-index)" = "e2f0c90a5f3459330ac8bc0d2f879c693bb7a2f59689c1083fc4ef83834da865" 2467 | "checksum time 0.1.42 (registry+https://github.com/rust-lang/crates.io-index)" = "db8dcfca086c1143c9270ac42a2bbd8a7ee477b78ac8e45b19abfb0cbede4b6f" 2468 | "checksum tokio 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)" = "bcced6bb623d4bff3739c176c415f13c418f426395c169c9c3cd9a492c715b16" 2469 | "checksum tokio-codec 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "5c501eceaf96f0e1793cf26beb63da3d11c738c4a943fdf3746d81d64684c39f" 2470 | "checksum tokio-current-thread 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "d16217cad7f1b840c5a97dfb3c43b0c871fef423a6e8d2118c604e843662a443" 2471 | "checksum tokio-executor 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "0f27ee0e6db01c5f0b2973824547ce7e637b2ed79b891a9677b0de9bd532b6ac" 2472 | "checksum tokio-io 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)" = "5090db468dad16e1a7a54c8c67280c5e4b544f3d3e018f0b913b400261f85926" 2473 | "checksum tokio-postgres 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "c03cb0c66092269a9b280e9e4956cb23ce00b8a6b1b393f7700f7732ac4bf133" 2474 | "checksum tokio-reactor 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "6af16bfac7e112bea8b0442542161bfc41cbfa4466b580bdda7d18cb88b911ce" 2475 | "checksum tokio-signal 0.2.7 (registry+https://github.com/rust-lang/crates.io-index)" = "dd6dc5276ea05ce379a16de90083ec80836440d5ef8a6a39545a3207373b8296" 2476 | "checksum tokio-sync 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "2162248ff317e2bc713b261f242b69dbb838b85248ed20bb21df56d60ea4cae7" 2477 | "checksum tokio-tcp 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "1d14b10654be682ac43efee27401d792507e30fd8d26389e1da3b185de2e4119" 2478 | "checksum tokio-timer 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "f2106812d500ed25a4f38235b9cae8f78a09edf43203e16e59c3b769a342a60e" 2479 | "checksum tokio-udp 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "66268575b80f4a4a710ef83d087fdfeeabdce9b74c797535fbac18a2cb906e92" 2480 | "checksum tokio-util 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "571da51182ec208780505a32528fc5512a8fe1443ab960b3f2f3ef093cd16930" 2481 | "checksum toml 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)" = "758664fc71a3a69038656bee8b6be6477d2a6c315a6b81f7081f591bffa4111f" 2482 | "checksum trust-dns-proto 0.7.4 (registry+https://github.com/rust-lang/crates.io-index)" = "5559ebdf6c2368ddd11e20b11d6bbaf9e46deb803acd7815e93f5a7b4a6d2901" 2483 | "checksum trust-dns-resolver 0.11.1 (registry+https://github.com/rust-lang/crates.io-index)" = "6c9992e58dba365798803c0b91018ff6c8d3fc77e06977c4539af2a6bfe0a039" 2484 | "checksum typenum 1.11.2 (registry+https://github.com/rust-lang/crates.io-index)" = "6d2783fe2d6b8c1101136184eb41be8b1ad379e4657050b8aaff0c79ee7575f9" 2485 | "checksum ucd-util 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "535c204ee4d8434478593480b8f86ab45ec9aae0e83c568ca81abf0fd0e88f86" 2486 | "checksum unicase 2.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "a84e5511b2a947f3ae965dcb29b13b7b1691b6e7332cf5dbc1744138d5acb7f6" 2487 | "checksum unicode-bidi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "49f2bd0c6468a8230e1db229cff8029217cf623c767ea5d60bfbd42729ea54d5" 2488 | "checksum unicode-normalization 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "141339a08b982d942be2ca06ff8b076563cbe223d1befd5450716790d44e2426" 2489 | "checksum unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc" 2490 | "checksum unicode-xid 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "826e7639553986605ec5979c7dd957c7895e93eabed50ab2ffa7f6128a75097c" 2491 | "checksum url 1.7.2 (registry+https://github.com/rust-lang/crates.io-index)" = "dd4e7c0d531266369519a4aa4f399d748bd37043b00bde1e4ff1f60a120b355a" 2492 | "checksum utf8-ranges 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)" = "9d50aa7650df78abf942826607c62468ce18d9019673d4a2ebe1865dbb96ffde" 2493 | "checksum version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "914b1a6776c4c929a602fafd8bc742e06365d4bcbe48c30f9cca5824f70dc9dd" 2494 | "checksum widestring 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "effc0e4ff8085673ea7b9b2e3c73f6bd4d118810c9009ed8f1e16bd96c331db6" 2495 | "checksum winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" 2496 | "checksum winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)" = "f10e386af2b13e47c89e7236a7a14a086791a2b88ebad6df9bf42040195cf770" 2497 | "checksum winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc" 2498 | "checksum winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" 2499 | "checksum winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" 2500 | "checksum winreg 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)" = "daf67b95d0b1bf421c4f11048d63110ca3719977169eec86396b614c8942b6e0" 2501 | "checksum winutil 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7daf138b6b14196e3830a588acf1e86966c694d3e8fb026fb105b8b5dca07e6e" 2502 | "checksum ws2_32-sys 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "d59cefebd0c892fa2dd6de581e937301d8552cb44489cdff035c6187cb63fa5e" 2503 | "checksum yaml-rust 0.4.3 (registry+https://github.com/rust-lang/crates.io-index)" = "65923dd1784f44da1d2c3dbbc5e822045628c590ba72123e1c73d3c230c4434d" 2504 | -------------------------------------------------------------------------------- /Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "SpamWatchAPI" 3 | version = "0.4.0" 4 | authors = ["SitiSchu "] 5 | edition = "2018" 6 | description = "API for t.me/SpamWatch to query User IDs for their ban status and reason." 7 | homepage = "https://github.com/SpamWatch/SpamWatchAPI" 8 | repository = "https://github.com/SpamWatch/SpamWatchAPI" 9 | license = "AGPL-3.0" 10 | 11 | [dependencies] 12 | nanoid = "0.2" 13 | config = "0.9" 14 | actix-web = "1.0" 15 | slog = "2.4" 16 | slog-term = "2.4" 17 | slog-async = "2.3.0" 18 | serde = "1.0.8" 19 | serde_json = "1.0.2" 20 | dirs = "2.0" 21 | failure = "0.1" 22 | lazy_static = "1.3.0" 23 | chrono = { version = "0.4", features = ["serde"] } 24 | postgres = "0.17" 25 | postgres-types = { version = "0.1", features = ["derive", "with-chrono-0_4"] } 26 | 27 | [dev-dependencies] 28 | actix-service = "0.4" 29 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | GNU AFFERO GENERAL PUBLIC LICENSE 2 | Version 3, 19 November 2007 3 | 4 | Copyright (C) 2007 Free Software Foundation, Inc. 5 | Everyone is permitted to copy and distribute verbatim copies 6 | of this license document, but changing it is not allowed. 7 | 8 | Preamble 9 | 10 | The GNU Affero General Public License is a free, copyleft license for 11 | software and other kinds of works, specifically designed to ensure 12 | cooperation with the community in the case of network server software. 13 | 14 | The licenses for most software and other practical works are designed 15 | to take away your freedom to share and change the works. By contrast, 16 | our General Public Licenses are intended to guarantee your freedom to 17 | share and change all versions of a program--to make sure it remains free 18 | software for all its users. 19 | 20 | When we speak of free software, we are referring to freedom, not 21 | price. Our General Public Licenses are designed to make sure that you 22 | have the freedom to distribute copies of free software (and charge for 23 | them if you wish), that you receive source code or can get it if you 24 | want it, that you can change the software or use pieces of it in new 25 | free programs, and that you know you can do these things. 26 | 27 | Developers that use our General Public Licenses protect your rights 28 | with two steps: (1) assert copyright on the software, and (2) offer 29 | you this License which gives you legal permission to copy, distribute 30 | and/or modify the software. 31 | 32 | A secondary benefit of defending all users' freedom is that 33 | improvements made in alternate versions of the program, if they 34 | receive widespread use, become available for other developers to 35 | incorporate. Many developers of free software are heartened and 36 | encouraged by the resulting cooperation. However, in the case of 37 | software used on network servers, this result may fail to come about. 38 | The GNU General Public License permits making a modified version and 39 | letting the public access it on a server without ever releasing its 40 | source code to the public. 41 | 42 | The GNU Affero General Public License is designed specifically to 43 | ensure that, in such cases, the modified source code becomes available 44 | to the community. It requires the operator of a network server to 45 | provide the source code of the modified version running there to the 46 | users of that server. Therefore, public use of a modified version, on 47 | a publicly accessible server, gives the public access to the source 48 | code of the modified version. 49 | 50 | An older license, called the Affero General Public License and 51 | published by Affero, was designed to accomplish similar goals. This is 52 | a different license, not a version of the Affero GPL, but Affero has 53 | released a new version of the Affero GPL which permits relicensing under 54 | this license. 55 | 56 | The precise terms and conditions for copying, distribution and 57 | modification follow. 58 | 59 | TERMS AND CONDITIONS 60 | 61 | 0. Definitions. 62 | 63 | "This License" refers to version 3 of the GNU Affero General Public License. 64 | 65 | "Copyright" also means copyright-like laws that apply to other kinds of 66 | works, such as semiconductor masks. 67 | 68 | "The Program" refers to any copyrightable work licensed under this 69 | License. Each licensee is addressed as "you". "Licensees" and 70 | "recipients" may be individuals or organizations. 71 | 72 | To "modify" a work means to copy from or adapt all or part of the work 73 | in a fashion requiring copyright permission, other than the making of an 74 | exact copy. The resulting work is called a "modified version" of the 75 | earlier work or a work "based on" the earlier work. 76 | 77 | A "covered work" means either the unmodified Program or a work based 78 | on the Program. 79 | 80 | To "propagate" a work means to do anything with it that, without 81 | permission, would make you directly or secondarily liable for 82 | infringement under applicable copyright law, except executing it on a 83 | computer or modifying a private copy. Propagation includes copying, 84 | distribution (with or without modification), making available to the 85 | public, and in some countries other activities as well. 86 | 87 | To "convey" a work means any kind of propagation that enables other 88 | parties to make or receive copies. Mere interaction with a user through 89 | a computer network, with no transfer of a copy, is not conveying. 90 | 91 | An interactive user interface displays "Appropriate Legal Notices" 92 | to the extent that it includes a convenient and prominently visible 93 | feature that (1) displays an appropriate copyright notice, and (2) 94 | tells the user that there is no warranty for the work (except to the 95 | extent that warranties are provided), that licensees may convey the 96 | work under this License, and how to view a copy of this License. If 97 | the interface presents a list of user commands or options, such as a 98 | menu, a prominent item in the list meets this criterion. 99 | 100 | 1. Source Code. 101 | 102 | The "source code" for a work means the preferred form of the work 103 | for making modifications to it. "Object code" means any non-source 104 | form of a work. 105 | 106 | A "Standard Interface" means an interface that either is an official 107 | standard defined by a recognized standards body, or, in the case of 108 | interfaces specified for a particular programming language, one that 109 | is widely used among developers working in that language. 110 | 111 | The "System Libraries" of an executable work include anything, other 112 | than the work as a whole, that (a) is included in the normal form of 113 | packaging a Major Component, but which is not part of that Major 114 | Component, and (b) serves only to enable use of the work with that 115 | Major Component, or to implement a Standard Interface for which an 116 | implementation is available to the public in source code form. A 117 | "Major Component", in this context, means a major essential component 118 | (kernel, window system, and so on) of the specific operating system 119 | (if any) on which the executable work runs, or a compiler used to 120 | produce the work, or an object code interpreter used to run it. 121 | 122 | The "Corresponding Source" for a work in object code form means all 123 | the source code needed to generate, install, and (for an executable 124 | work) run the object code and to modify the work, including scripts to 125 | control those activities. However, it does not include the work's 126 | System Libraries, or general-purpose tools or generally available free 127 | programs which are used unmodified in performing those activities but 128 | which are not part of the work. For example, Corresponding Source 129 | includes interface definition files associated with source files for 130 | the work, and the source code for shared libraries and dynamically 131 | linked subprograms that the work is specifically designed to require, 132 | such as by intimate data communication or control flow between those 133 | subprograms and other parts of the work. 134 | 135 | The Corresponding Source need not include anything that users 136 | can regenerate automatically from other parts of the Corresponding 137 | Source. 138 | 139 | The Corresponding Source for a work in source code form is that 140 | same work. 141 | 142 | 2. Basic Permissions. 143 | 144 | All rights granted under this License are granted for the term of 145 | copyright on the Program, and are irrevocable provided the stated 146 | conditions are met. This License explicitly affirms your unlimited 147 | permission to run the unmodified Program. The output from running a 148 | covered work is covered by this License only if the output, given its 149 | content, constitutes a covered work. This License acknowledges your 150 | rights of fair use or other equivalent, as provided by copyright law. 151 | 152 | You may make, run and propagate covered works that you do not 153 | convey, without conditions so long as your license otherwise remains 154 | in force. You may convey covered works to others for the sole purpose 155 | of having them make modifications exclusively for you, or provide you 156 | with facilities for running those works, provided that you comply with 157 | the terms of this License in conveying all material for which you do 158 | not control copyright. Those thus making or running the covered works 159 | for you must do so exclusively on your behalf, under your direction 160 | and control, on terms that prohibit them from making any copies of 161 | your copyrighted material outside their relationship with you. 162 | 163 | Conveying under any other circumstances is permitted solely under 164 | the conditions stated below. Sublicensing is not allowed; section 10 165 | makes it unnecessary. 166 | 167 | 3. Protecting Users' Legal Rights From Anti-Circumvention Law. 168 | 169 | No covered work shall be deemed part of an effective technological 170 | measure under any applicable law fulfilling obligations under article 171 | 11 of the WIPO copyright treaty adopted on 20 December 1996, or 172 | similar laws prohibiting or restricting circumvention of such 173 | measures. 174 | 175 | When you convey a covered work, you waive any legal power to forbid 176 | circumvention of technological measures to the extent such circumvention 177 | is effected by exercising rights under this License with respect to 178 | the covered work, and you disclaim any intention to limit operation or 179 | modification of the work as a means of enforcing, against the work's 180 | users, your or third parties' legal rights to forbid circumvention of 181 | technological measures. 182 | 183 | 4. Conveying Verbatim Copies. 184 | 185 | You may convey verbatim copies of the Program's source code as you 186 | receive it, in any medium, provided that you conspicuously and 187 | appropriately publish on each copy an appropriate copyright notice; 188 | keep intact all notices stating that this License and any 189 | non-permissive terms added in accord with section 7 apply to the code; 190 | keep intact all notices of the absence of any warranty; and give all 191 | recipients a copy of this License along with the Program. 192 | 193 | You may charge any price or no price for each copy that you convey, 194 | and you may offer support or warranty protection for a fee. 195 | 196 | 5. Conveying Modified Source Versions. 197 | 198 | You may convey a work based on the Program, or the modifications to 199 | produce it from the Program, in the form of source code under the 200 | terms of section 4, provided that you also meet all of these conditions: 201 | 202 | a) The work must carry prominent notices stating that you modified 203 | it, and giving a relevant date. 204 | 205 | b) The work must carry prominent notices stating that it is 206 | released under this License and any conditions added under section 207 | 7. This requirement modifies the requirement in section 4 to 208 | "keep intact all notices". 209 | 210 | c) You must license the entire work, as a whole, under this 211 | License to anyone who comes into possession of a copy. This 212 | License will therefore apply, along with any applicable section 7 213 | additional terms, to the whole of the work, and all its parts, 214 | regardless of how they are packaged. This License gives no 215 | permission to license the work in any other way, but it does not 216 | invalidate such permission if you have separately received it. 217 | 218 | d) If the work has interactive user interfaces, each must display 219 | Appropriate Legal Notices; however, if the Program has interactive 220 | interfaces that do not display Appropriate Legal Notices, your 221 | work need not make them do so. 222 | 223 | A compilation of a covered work with other separate and independent 224 | works, which are not by their nature extensions of the covered work, 225 | and which are not combined with it such as to form a larger program, 226 | in or on a volume of a storage or distribution medium, is called an 227 | "aggregate" if the compilation and its resulting copyright are not 228 | used to limit the access or legal rights of the compilation's users 229 | beyond what the individual works permit. Inclusion of a covered work 230 | in an aggregate does not cause this License to apply to the other 231 | parts of the aggregate. 232 | 233 | 6. Conveying Non-Source Forms. 234 | 235 | You may convey a covered work in object code form under the terms 236 | of sections 4 and 5, provided that you also convey the 237 | machine-readable Corresponding Source under the terms of this License, 238 | in one of these ways: 239 | 240 | a) Convey the object code in, or embodied in, a physical product 241 | (including a physical distribution medium), accompanied by the 242 | Corresponding Source fixed on a durable physical medium 243 | customarily used for software interchange. 244 | 245 | b) Convey the object code in, or embodied in, a physical product 246 | (including a physical distribution medium), accompanied by a 247 | written offer, valid for at least three years and valid for as 248 | long as you offer spare parts or customer support for that product 249 | model, to give anyone who possesses the object code either (1) a 250 | copy of the Corresponding Source for all the software in the 251 | product that is covered by this License, on a durable physical 252 | medium customarily used for software interchange, for a price no 253 | more than your reasonable cost of physically performing this 254 | conveying of source, or (2) access to copy the 255 | Corresponding Source from a network server at no charge. 256 | 257 | c) Convey individual copies of the object code with a copy of the 258 | written offer to provide the Corresponding Source. This 259 | alternative is allowed only occasionally and noncommercially, and 260 | only if you received the object code with such an offer, in accord 261 | with subsection 6b. 262 | 263 | d) Convey the object code by offering access from a designated 264 | place (gratis or for a charge), and offer equivalent access to the 265 | Corresponding Source in the same way through the same place at no 266 | further charge. You need not require recipients to copy the 267 | Corresponding Source along with the object code. If the place to 268 | copy the object code is a network server, the Corresponding Source 269 | may be on a different server (operated by you or a third party) 270 | that supports equivalent copying facilities, provided you maintain 271 | clear directions next to the object code saying where to find the 272 | Corresponding Source. Regardless of what server hosts the 273 | Corresponding Source, you remain obligated to ensure that it is 274 | available for as long as needed to satisfy these requirements. 275 | 276 | e) Convey the object code using peer-to-peer transmission, provided 277 | you inform other peers where the object code and Corresponding 278 | Source of the work are being offered to the general public at no 279 | charge under subsection 6d. 280 | 281 | A separable portion of the object code, whose source code is excluded 282 | from the Corresponding Source as a System Library, need not be 283 | included in conveying the object code work. 284 | 285 | A "User Product" is either (1) a "consumer product", which means any 286 | tangible personal property which is normally used for personal, family, 287 | or household purposes, or (2) anything designed or sold for incorporation 288 | into a dwelling. In determining whether a product is a consumer product, 289 | doubtful cases shall be resolved in favor of coverage. For a particular 290 | product received by a particular user, "normally used" refers to a 291 | typical or common use of that class of product, regardless of the status 292 | of the particular user or of the way in which the particular user 293 | actually uses, or expects or is expected to use, the product. A product 294 | is a consumer product regardless of whether the product has substantial 295 | commercial, industrial or non-consumer uses, unless such uses represent 296 | the only significant mode of use of the product. 297 | 298 | "Installation Information" for a User Product means any methods, 299 | procedures, authorization keys, or other information required to install 300 | and execute modified versions of a covered work in that User Product from 301 | a modified version of its Corresponding Source. The information must 302 | suffice to ensure that the continued functioning of the modified object 303 | code is in no case prevented or interfered with solely because 304 | modification has been made. 305 | 306 | If you convey an object code work under this section in, or with, or 307 | specifically for use in, a User Product, and the conveying occurs as 308 | part of a transaction in which the right of possession and use of the 309 | User Product is transferred to the recipient in perpetuity or for a 310 | fixed term (regardless of how the transaction is characterized), the 311 | Corresponding Source conveyed under this section must be accompanied 312 | by the Installation Information. But this requirement does not apply 313 | if neither you nor any third party retains the ability to install 314 | modified object code on the User Product (for example, the work has 315 | been installed in ROM). 316 | 317 | The requirement to provide Installation Information does not include a 318 | requirement to continue to provide support service, warranty, or updates 319 | for a work that has been modified or installed by the recipient, or for 320 | the User Product in which it has been modified or installed. Access to a 321 | network may be denied when the modification itself materially and 322 | adversely affects the operation of the network or violates the rules and 323 | protocols for communication across the network. 324 | 325 | Corresponding Source conveyed, and Installation Information provided, 326 | in accord with this section must be in a format that is publicly 327 | documented (and with an implementation available to the public in 328 | source code form), and must require no special password or key for 329 | unpacking, reading or copying. 330 | 331 | 7. Additional Terms. 332 | 333 | "Additional permissions" are terms that supplement the terms of this 334 | License by making exceptions from one or more of its conditions. 335 | Additional permissions that are applicable to the entire Program shall 336 | be treated as though they were included in this License, to the extent 337 | that they are valid under applicable law. If additional permissions 338 | apply only to part of the Program, that part may be used separately 339 | under those permissions, but the entire Program remains governed by 340 | this License without regard to the additional permissions. 341 | 342 | When you convey a copy of a covered work, you may at your option 343 | remove any additional permissions from that copy, or from any part of 344 | it. (Additional permissions may be written to require their own 345 | removal in certain cases when you modify the work.) You may place 346 | additional permissions on material, added by you to a covered work, 347 | for which you have or can give appropriate copyright permission. 348 | 349 | Notwithstanding any other provision of this License, for material you 350 | add to a covered work, you may (if authorized by the copyright holders of 351 | that material) supplement the terms of this License with terms: 352 | 353 | a) Disclaiming warranty or limiting liability differently from the 354 | terms of sections 15 and 16 of this License; or 355 | 356 | b) Requiring preservation of specified reasonable legal notices or 357 | author attributions in that material or in the Appropriate Legal 358 | Notices displayed by works containing it; or 359 | 360 | c) Prohibiting misrepresentation of the origin of that material, or 361 | requiring that modified versions of such material be marked in 362 | reasonable ways as different from the original version; or 363 | 364 | d) Limiting the use for publicity purposes of names of licensors or 365 | authors of the material; or 366 | 367 | e) Declining to grant rights under trademark law for use of some 368 | trade names, trademarks, or service marks; or 369 | 370 | f) Requiring indemnification of licensors and authors of that 371 | material by anyone who conveys the material (or modified versions of 372 | it) with contractual assumptions of liability to the recipient, for 373 | any liability that these contractual assumptions directly impose on 374 | those licensors and authors. 375 | 376 | All other non-permissive additional terms are considered "further 377 | restrictions" within the meaning of section 10. If the Program as you 378 | received it, or any part of it, contains a notice stating that it is 379 | governed by this License along with a term that is a further 380 | restriction, you may remove that term. If a license document contains 381 | a further restriction but permits relicensing or conveying under this 382 | License, you may add to a covered work material governed by the terms 383 | of that license document, provided that the further restriction does 384 | not survive such relicensing or conveying. 385 | 386 | If you add terms to a covered work in accord with this section, you 387 | must place, in the relevant source files, a statement of the 388 | additional terms that apply to those files, or a notice indicating 389 | where to find the applicable terms. 390 | 391 | Additional terms, permissive or non-permissive, may be stated in the 392 | form of a separately written license, or stated as exceptions; 393 | the above requirements apply either way. 394 | 395 | 8. Termination. 396 | 397 | You may not propagate or modify a covered work except as expressly 398 | provided under this License. Any attempt otherwise to propagate or 399 | modify it is void, and will automatically terminate your rights under 400 | this License (including any patent licenses granted under the third 401 | paragraph of section 11). 402 | 403 | However, if you cease all violation of this License, then your 404 | license from a particular copyright holder is reinstated (a) 405 | provisionally, unless and until the copyright holder explicitly and 406 | finally terminates your license, and (b) permanently, if the copyright 407 | holder fails to notify you of the violation by some reasonable means 408 | prior to 60 days after the cessation. 409 | 410 | Moreover, your license from a particular copyright holder is 411 | reinstated permanently if the copyright holder notifies you of the 412 | violation by some reasonable means, this is the first time you have 413 | received notice of violation of this License (for any work) from that 414 | copyright holder, and you cure the violation prior to 30 days after 415 | your receipt of the notice. 416 | 417 | Termination of your rights under this section does not terminate the 418 | licenses of parties who have received copies or rights from you under 419 | this License. If your rights have been terminated and not permanently 420 | reinstated, you do not qualify to receive new licenses for the same 421 | material under section 10. 422 | 423 | 9. Acceptance Not Required for Having Copies. 424 | 425 | You are not required to accept this License in order to receive or 426 | run a copy of the Program. Ancillary propagation of a covered work 427 | occurring solely as a consequence of using peer-to-peer transmission 428 | to receive a copy likewise does not require acceptance. However, 429 | nothing other than this License grants you permission to propagate or 430 | modify any covered work. These actions infringe copyright if you do 431 | not accept this License. Therefore, by modifying or propagating a 432 | covered work, you indicate your acceptance of this License to do so. 433 | 434 | 10. Automatic Licensing of Downstream Recipients. 435 | 436 | Each time you convey a covered work, the recipient automatically 437 | receives a license from the original licensors, to run, modify and 438 | propagate that work, subject to this License. You are not responsible 439 | for enforcing compliance by third parties with this License. 440 | 441 | An "entity transaction" is a transaction transferring control of an 442 | organization, or substantially all assets of one, or subdividing an 443 | organization, or merging organizations. If propagation of a covered 444 | work results from an entity transaction, each party to that 445 | transaction who receives a copy of the work also receives whatever 446 | licenses to the work the party's predecessor in interest had or could 447 | give under the previous paragraph, plus a right to possession of the 448 | Corresponding Source of the work from the predecessor in interest, if 449 | the predecessor has it or can get it with reasonable efforts. 450 | 451 | You may not impose any further restrictions on the exercise of the 452 | rights granted or affirmed under this License. For example, you may 453 | not impose a license fee, royalty, or other charge for exercise of 454 | rights granted under this License, and you may not initiate litigation 455 | (including a cross-claim or counterclaim in a lawsuit) alleging that 456 | any patent claim is infringed by making, using, selling, offering for 457 | sale, or importing the Program or any portion of it. 458 | 459 | 11. Patents. 460 | 461 | A "contributor" is a copyright holder who authorizes use under this 462 | License of the Program or a work on which the Program is based. The 463 | work thus licensed is called the contributor's "contributor version". 464 | 465 | A contributor's "essential patent claims" are all patent claims 466 | owned or controlled by the contributor, whether already acquired or 467 | hereafter acquired, that would be infringed by some manner, permitted 468 | by this License, of making, using, or selling its contributor version, 469 | but do not include claims that would be infringed only as a 470 | consequence of further modification of the contributor version. For 471 | purposes of this definition, "control" includes the right to grant 472 | patent sublicenses in a manner consistent with the requirements of 473 | this License. 474 | 475 | Each contributor grants you a non-exclusive, worldwide, royalty-free 476 | patent license under the contributor's essential patent claims, to 477 | make, use, sell, offer for sale, import and otherwise run, modify and 478 | propagate the contents of its contributor version. 479 | 480 | In the following three paragraphs, a "patent license" is any express 481 | agreement or commitment, however denominated, not to enforce a patent 482 | (such as an express permission to practice a patent or covenant not to 483 | sue for patent infringement). To "grant" such a patent license to a 484 | party means to make such an agreement or commitment not to enforce a 485 | patent against the party. 486 | 487 | If you convey a covered work, knowingly relying on a patent license, 488 | and the Corresponding Source of the work is not available for anyone 489 | to copy, free of charge and under the terms of this License, through a 490 | publicly available network server or other readily accessible means, 491 | then you must either (1) cause the Corresponding Source to be so 492 | available, or (2) arrange to deprive yourself of the benefit of the 493 | patent license for this particular work, or (3) arrange, in a manner 494 | consistent with the requirements of this License, to extend the patent 495 | license to downstream recipients. "Knowingly relying" means you have 496 | actual knowledge that, but for the patent license, your conveying the 497 | covered work in a country, or your recipient's use of the covered work 498 | in a country, would infringe one or more identifiable patents in that 499 | country that you have reason to believe are valid. 500 | 501 | If, pursuant to or in connection with a single transaction or 502 | arrangement, you convey, or propagate by procuring conveyance of, a 503 | covered work, and grant a patent license to some of the parties 504 | receiving the covered work authorizing them to use, propagate, modify 505 | or convey a specific copy of the covered work, then the patent license 506 | you grant is automatically extended to all recipients of the covered 507 | work and works based on it. 508 | 509 | A patent license is "discriminatory" if it does not include within 510 | the scope of its coverage, prohibits the exercise of, or is 511 | conditioned on the non-exercise of one or more of the rights that are 512 | specifically granted under this License. You may not convey a covered 513 | work if you are a party to an arrangement with a third party that is 514 | in the business of distributing software, under which you make payment 515 | to the third party based on the extent of your activity of conveying 516 | the work, and under which the third party grants, to any of the 517 | parties who would receive the covered work from you, a discriminatory 518 | patent license (a) in connection with copies of the covered work 519 | conveyed by you (or copies made from those copies), or (b) primarily 520 | for and in connection with specific products or compilations that 521 | contain the covered work, unless you entered into that arrangement, 522 | or that patent license was granted, prior to 28 March 2007. 523 | 524 | Nothing in this License shall be construed as excluding or limiting 525 | any implied license or other defenses to infringement that may 526 | otherwise be available to you under applicable patent law. 527 | 528 | 12. No Surrender of Others' Freedom. 529 | 530 | If conditions are imposed on you (whether by court order, agreement or 531 | otherwise) that contradict the conditions of this License, they do not 532 | excuse you from the conditions of this License. If you cannot convey a 533 | covered work so as to satisfy simultaneously your obligations under this 534 | License and any other pertinent obligations, then as a consequence you may 535 | not convey it at all. For example, if you agree to terms that obligate you 536 | to collect a royalty for further conveying from those to whom you convey 537 | the Program, the only way you could satisfy both those terms and this 538 | License would be to refrain entirely from conveying the Program. 539 | 540 | 13. Remote Network Interaction; Use with the GNU General Public License. 541 | 542 | Notwithstanding any other provision of this License, if you modify the 543 | Program, your modified version must prominently offer all users 544 | interacting with it remotely through a computer network (if your version 545 | supports such interaction) an opportunity to receive the Corresponding 546 | Source of your version by providing access to the Corresponding Source 547 | from a network server at no charge, through some standard or customary 548 | means of facilitating copying of software. This Corresponding Source 549 | shall include the Corresponding Source for any work covered by version 3 550 | of the GNU General Public License that is incorporated pursuant to the 551 | following paragraph. 552 | 553 | Notwithstanding any other provision of this License, you have 554 | permission to link or combine any covered work with a work licensed 555 | under version 3 of the GNU General Public License into a single 556 | combined work, and to convey the resulting work. The terms of this 557 | License will continue to apply to the part which is the covered work, 558 | but the work with which it is combined will remain governed by version 559 | 3 of the GNU General Public License. 560 | 561 | 14. Revised Versions of this License. 562 | 563 | The Free Software Foundation may publish revised and/or new versions of 564 | the GNU Affero General Public License from time to time. Such new versions 565 | will be similar in spirit to the present version, but may differ in detail to 566 | address new problems or concerns. 567 | 568 | Each version is given a distinguishing version number. If the 569 | Program specifies that a certain numbered version of the GNU Affero General 570 | Public License "or any later version" applies to it, you have the 571 | option of following the terms and conditions either of that numbered 572 | version or of any later version published by the Free Software 573 | Foundation. If the Program does not specify a version number of the 574 | GNU Affero General Public License, you may choose any version ever published 575 | by the Free Software Foundation. 576 | 577 | If the Program specifies that a proxy can decide which future 578 | versions of the GNU Affero General Public License can be used, that proxy's 579 | public statement of acceptance of a version permanently authorizes you 580 | to choose that version for the Program. 581 | 582 | Later license versions may give you additional or different 583 | permissions. However, no additional obligations are imposed on any 584 | author or copyright holder as a result of your choosing to follow a 585 | later version. 586 | 587 | 15. Disclaimer of Warranty. 588 | 589 | THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY 590 | APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT 591 | HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY 592 | OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, 593 | THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 594 | PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM 595 | IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF 596 | ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 597 | 598 | 16. Limitation of Liability. 599 | 600 | IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING 601 | WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS 602 | THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY 603 | GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE 604 | USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF 605 | DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD 606 | PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), 607 | EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF 608 | SUCH DAMAGES. 609 | 610 | 17. Interpretation of Sections 15 and 16. 611 | 612 | If the disclaimer of warranty and limitation of liability provided 613 | above cannot be given local legal effect according to their terms, 614 | reviewing courts shall apply local law that most closely approximates 615 | an absolute waiver of all civil liability in connection with the 616 | Program, unless a warranty or assumption of liability accompanies a 617 | copy of the Program in return for a fee. 618 | 619 | END OF TERMS AND CONDITIONS 620 | 621 | How to Apply These Terms to Your New Programs 622 | 623 | If you develop a new program, and you want it to be of the greatest 624 | possible use to the public, the best way to achieve this is to make it 625 | free software which everyone can redistribute and change under these terms. 626 | 627 | To do so, attach the following notices to the program. It is safest 628 | to attach them to the start of each source file to most effectively 629 | state the exclusion of warranty; and each file should have at least 630 | the "copyright" line and a pointer to where the full notice is found. 631 | 632 | 633 | Copyright (C) 634 | 635 | This program is free software: you can redistribute it and/or modify 636 | it under the terms of the GNU Affero General Public License as published by 637 | the Free Software Foundation, either version 3 of the License, or 638 | (at your option) any later version. 639 | 640 | This program is distributed in the hope that it will be useful, 641 | but WITHOUT ANY WARRANTY; without even the implied warranty of 642 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 643 | GNU Affero General Public License for more details. 644 | 645 | You should have received a copy of the GNU Affero General Public License 646 | along with this program. If not, see . 647 | 648 | Also add information on how to contact you by electronic and paper mail. 649 | 650 | If your software can interact with users remotely through a computer 651 | network, you should also make sure that it provides a way for users to 652 | get its source. For example, if your program is a web application, its 653 | interface could display a "Source" link that leads users to an archive 654 | of the code. There are many ways you could offer source, and different 655 | solutions will be better for different programs; see section 13 for the 656 | specific requirements. 657 | 658 | You should also get your employer (if you work as a programmer) or school, 659 | if any, to sign a "copyright disclaimer" for the program, if necessary. 660 | For more information on this, and how to apply and follow the GNU AGPL, see 661 | . 662 | -------------------------------------------------------------------------------- /example.config.toml: -------------------------------------------------------------------------------- 1 | [general] 2 | # All fields are required for now 3 | token_size = 64 4 | # Telegram ID of the master account 5 | masterid = 777000 6 | 7 | [database] 8 | host = "127.0.0.1" 9 | password = "password" 10 | username = "SpamWatchAPI" 11 | name = "SpamWatchAPI" 12 | -------------------------------------------------------------------------------- /migrations/20200612002126_initial/down.sql: -------------------------------------------------------------------------------- 1 | DROP TABLE banlist; 2 | 3 | DROP TABLE tokens; 4 | 5 | DROP TYPE permission CASCADE; 6 | -------------------------------------------------------------------------------- /migrations/20200612002126_initial/up.sql: -------------------------------------------------------------------------------- 1 | DO $$ 2 | BEGIN 3 | IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'permission') THEN 4 | CREATE TYPE permission AS ENUM ('User', 'Admin', 'Root'); 5 | END IF; 6 | 7 | END$$; 8 | 9 | CREATE TABLE IF NOT EXISTS tokens 10 | ( 11 | id SERIAL PRIMARY KEY, 12 | token Text NOT NULL, 13 | permission permission NOT NULL, 14 | userid bigint NOT NULL, 15 | retired bool NOT NULL DEFAULT false 16 | ); 17 | 18 | CREATE TABLE IF NOT EXISTS banlist 19 | ( 20 | id bigint NOT NULL PRIMARY KEY, 21 | reason Text NOT NULL, 22 | date timestamp NOT NULL, 23 | admin_token integer references tokens (id) NOT NULL 24 | ); 25 | -------------------------------------------------------------------------------- /migrations/20200612004225_antiflood/down.sql: -------------------------------------------------------------------------------- 1 | DROP TABLE antiflood; 2 | -------------------------------------------------------------------------------- /migrations/20200612004225_antiflood/up.sql: -------------------------------------------------------------------------------- 1 | CREATE TABLE IF NOT EXISTS antiflood 2 | ( 3 | token integer references tokens (id) NOT NULL PRIMARY KEY, 4 | banlist_all timestamp NOT NULL 5 | ); 6 | -------------------------------------------------------------------------------- /migrations/20200612020854_message-field/down.sql: -------------------------------------------------------------------------------- 1 | ALTER TABLE banlist DROP COLUMN IF EXISTS message; 2 | -------------------------------------------------------------------------------- /migrations/20200612020854_message-field/up.sql: -------------------------------------------------------------------------------- 1 | ALTER TABLE banlist ADD COLUMN message text; 2 | -------------------------------------------------------------------------------- /shell.nix: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env nix-shell 2 | with import {}; 3 | stdenv.mkDerivation { 4 | name = "SpamWatchAPI"; 5 | buildInputs = [ postgresql ]; 6 | shellHook = 7 | '' 8 | export PGDATA=~/main/db/postgres 9 | mkdir -p $PGDATA 10 | initdb 11 | sudo mkdir /run/postgresql 12 | sudo chown $USER:users /run/postgresql 13 | pg_ctl -l /tmp/postgres.log start 14 | tail -f /tmp/postgres.log 15 | exit 16 | ''; 17 | } 18 | 19 | -------------------------------------------------------------------------------- /src/database.rs: -------------------------------------------------------------------------------- 1 | use chrono::NaiveDateTime; 2 | use postgres::{Client, Config, NoTls, Row}; 3 | use serde::Serialize; 4 | use serde_json::{json, Value}; 5 | 6 | use crate::errors::UserError; 7 | use crate::guards::Permission; 8 | use crate::settings; 9 | use crate::utils; 10 | 11 | pub struct Database { 12 | conn: Client, 13 | } 14 | 15 | #[derive(Debug, Serialize)] 16 | pub struct Token { 17 | pub id: i32, 18 | pub token: String, 19 | pub permission: Permission, 20 | pub userid: i64, 21 | pub retired: bool, 22 | } 23 | 24 | #[derive(Debug, Serialize)] 25 | pub struct Ban { 26 | pub id: i64, 27 | pub reason: String, 28 | pub date: chrono::NaiveDateTime, 29 | pub admin: i32, 30 | pub message: Option, 31 | } 32 | 33 | #[derive(Debug, Serialize)] 34 | pub struct Antiflood { 35 | pub banlist_all: NaiveDateTime, 36 | } 37 | 38 | impl Token { 39 | pub fn json(&self) -> Result { 40 | Ok(serde_json::to_value(&self)?) 41 | } 42 | } 43 | 44 | impl Ban { 45 | pub fn json(&self) -> Result { 46 | Ok(serde_json::to_value(self.raw_json())?) 47 | } 48 | 49 | pub fn raw_json(&self) -> Value { 50 | json!({ 51 | "id": self.id, 52 | "reason": self.reason, 53 | "date": self.date.timestamp(), 54 | "admin": self.admin, 55 | "message": self.message 56 | }) 57 | } 58 | } 59 | 60 | impl Default for Antiflood { 61 | fn default() -> Self { 62 | Antiflood { 63 | banlist_all: NaiveDateTime::from_timestamp(0, 0) 64 | } 65 | } 66 | } 67 | 68 | impl Database { 69 | pub fn new() -> Result { 70 | debug!(utils::LOGGER, "Connecting to database"; 71 | "host" => &settings::ENV.database.host, 72 | "port" => settings::ENV.database.port, 73 | "name" => &settings::ENV.database.name, 74 | "username" => &settings::ENV.database.username); 75 | let conn = Config::new() 76 | .host(&settings::ENV.database.host) 77 | .port(settings::ENV.database.port) 78 | .dbname(&settings::ENV.database.name) 79 | .user(&settings::ENV.database.username) 80 | .password(&settings::ENV.database.password) 81 | .application_name(&env!("CARGO_PKG_NAME")) 82 | .connect(NoTls)?; 83 | debug!(utils::LOGGER, "Connected to PostgreSQL"); 84 | Ok(Database { conn }) 85 | } 86 | 87 | //region Tokens 88 | pub fn create_genesis_token(&mut self) -> Result<(), postgres::Error> { 89 | let get_genesis_token = "SELECT * FROM tokens WHERE id = 1;"; 90 | debug!(utils::LOGGER, "Checking if Genesis Token exists"; 91 | "query" => get_genesis_token); 92 | if self.conn.query(get_genesis_token, &[])?.is_empty() { 93 | info!(utils::LOGGER, "Genesis Token doesn't exist. Creating one"; 94 | "size" => settings::ENV.general.token_size); 95 | let token = self.create_token(&Permission::Root, settings::ENV.general.masterid)?; 96 | info!(utils::LOGGER, "Created Genesis Token `{}`. Write this down, this will be the only time you see it.", token) 97 | } else { 98 | debug!(utils::LOGGER, "Genesis Token exists. Skipping creation.") 99 | } 100 | Ok(()) 101 | } 102 | 103 | pub fn get_tokens(&mut self) -> Result, postgres::Error> { 104 | let get_all_tokens = "SELECT * FROM tokens;"; 105 | debug!(utils::LOGGER, "Getting all tokens"; "query" => get_all_tokens); 106 | let result: Vec = self.conn.query(get_all_tokens, &[])?; 107 | Ok(result 108 | .into_iter() 109 | .map(|row| Token { 110 | id: row.get(0), 111 | token: row.get(1), 112 | permission: row.get(2), 113 | userid: row.get(3), 114 | retired: row.get(4), 115 | }) 116 | .collect()) 117 | } 118 | 119 | pub fn get_token_by_id(&mut self, token_id: i32) -> Result, postgres::Error> { 120 | let get_token_by_id = "SELECT * FROM tokens WHERE id = $1;"; 121 | debug!(utils::LOGGER, "Getting token by id"; 122 | "id" => token_id, "query" => get_token_by_id); 123 | let row: Option = self.conn.query(get_token_by_id, &[&token_id])?.pop(); 124 | 125 | Ok(match row { 126 | Some(token) => Some(Token { 127 | id: token.get(0), 128 | token: token.get(1), 129 | permission: token.get(2), 130 | userid: token.get(3), 131 | retired: token.get(4), 132 | }), 133 | None => None, 134 | }) 135 | } 136 | 137 | pub fn get_token_by_userid(&mut self, userid: i64) -> Result, postgres::Error> { 138 | let get_token_by_id = "SELECT * FROM tokens WHERE userid = $1;"; 139 | debug!(utils::LOGGER, "Getting token by userid"; 140 | "id" => userid, "query" => get_token_by_id); 141 | let result: Vec = self.conn.query(get_token_by_id, &[&userid])?; 142 | 143 | Ok(result 144 | .into_iter() 145 | .map(|row| Token { 146 | id: row.get(0), 147 | token: row.get(1), 148 | permission: row.get(2), 149 | userid: row.get(3), 150 | retired: row.get(4), 151 | }) 152 | .collect()) 153 | } 154 | 155 | pub fn get_token(&mut self, token: String) -> Result, postgres::Error> { 156 | let get_token_by_id = "SELECT * FROM tokens WHERE token = $1;"; 157 | debug!(utils::LOGGER, "Getting token"; "query" => get_token_by_id); 158 | let row: Option = self.conn.query(get_token_by_id, &[&token])?.pop(); 159 | 160 | Ok(match row { 161 | Some(token) => Some(Token { 162 | id: token.get(0), 163 | token: token.get(1), 164 | permission: token.get(2), 165 | userid: token.get(3), 166 | retired: token.get(4), 167 | }), 168 | None => None, 169 | }) 170 | } 171 | 172 | pub fn create_token( 173 | &mut self, 174 | permission: &Permission, 175 | userid: i64, 176 | ) -> Result { 177 | let token = nanoid::generate(settings::ENV.general.token_size as usize); 178 | let insert_token = " 179 | INSERT INTO tokens ( 180 | token, 181 | permission, 182 | userid) 183 | VALUES ($1, $2, $3);"; 184 | debug!(utils::LOGGER, "Creating Token"; 185 | "query" => insert_token, "permission" => format!("{:?}", permission)); 186 | self.conn.execute(insert_token, &[&token, &permission, &userid])?; 187 | Ok(token) 188 | } 189 | 190 | pub fn revoke_token_by_id(&mut self, token_id: i32) -> Result<(), postgres::Error> { 191 | let revoke_token_by_id = "UPDATE tokens SET retired = true WHERE id = $1;"; 192 | debug!(utils::LOGGER, "Revoking token by id"; 193 | "id" => token_id, "query" => revoke_token_by_id); 194 | self.conn.query(revoke_token_by_id, &[&token_id])?; 195 | Ok(()) 196 | } 197 | //endregion 198 | 199 | //region Banlist 200 | pub fn get_bans(&mut self) -> Result, postgres::Error> { 201 | let get_all_bans = "SELECT * FROM banlist;"; 202 | debug!(utils::LOGGER, "Getting all bans"; "query" => get_all_bans); 203 | let result: Vec = self.conn.query(get_all_bans, &[])?; 204 | Ok(result 205 | .into_iter() 206 | .map(|row| Ban { 207 | id: row.get(0), 208 | reason: row.get(1), 209 | date: row.get(2), 210 | admin: row.get(3), 211 | message: row.try_get(4).unwrap_or(Some("test".to_string())), 212 | }) 213 | .collect()) 214 | } 215 | 216 | pub fn get_banned_ids(&mut self) -> Result, postgres::Error> { 217 | let get_all_bans = "SELECT id FROM banlist;"; 218 | debug!(utils::LOGGER, "Getting all bans as ids"; "query" => get_all_bans); 219 | let result: Vec = self.conn.query(get_all_bans, &[])?; 220 | Ok(result 221 | .into_iter() 222 | .map(|row| row.get(0)) 223 | .collect()) 224 | } 225 | 226 | pub fn get_total_ban_count(&mut self) -> Result { 227 | let get_all_bans = "SELECT COUNT(*) FROM banlist;"; 228 | debug!(utils::LOGGER, "Getting all bans"; "query" => get_all_bans); 229 | let result: Vec = self.conn.query(get_all_bans, &[])?; 230 | let count = match result.get(0) { 231 | Some(row) => row.get(0), 232 | None => 0 233 | }; 234 | Ok(count) 235 | } 236 | 237 | pub fn add_ban(&mut self, user_id: i64, reason: &String, admin_token: i32, message: &Option) -> Result<(), postgres::Error> { 238 | let upsert_ban = " 239 | INSERT INTO banlist 240 | VALUES ($1, $2, now(), $3, $4) 241 | ON CONFLICT (id) DO 242 | UPDATE SET reason=excluded.reason, date=excluded.date, message=excluded.message;"; 243 | debug!(utils::LOGGER, "Upserting ban"; 244 | "id" => &user_id, "reason" => &reason, "query" => upsert_ban); 245 | self.conn.query(upsert_ban, &[&user_id, &reason, &admin_token, &message])?; 246 | Ok(()) 247 | } 248 | 249 | pub fn get_ban(&mut self, user_id: i64) -> Result, postgres::Error> { 250 | let get_ban = "SELECT * FROM banlist WHERE id = $1;"; 251 | debug!(utils::LOGGER, "Getting token by id"; 252 | "id" => user_id, "query" => get_ban); 253 | let row: Option = self.conn.query(get_ban, &[&user_id])?.pop(); 254 | 255 | Ok(match row { 256 | Some(ban) => Some(Ban { 257 | id: ban.get(0), 258 | reason: ban.get(1), 259 | date: ban.get(2), 260 | admin: ban.get(3), 261 | message: ban.try_get(4).unwrap_or(None), 262 | }), 263 | None => None, 264 | }) 265 | } 266 | 267 | pub fn delete_ban(&mut self, user_id: i64) -> Result<(), postgres::Error> { 268 | let delete_ban = "DELETE FROM banlist WHERE id = $1;"; 269 | debug!(utils::LOGGER, "Deleting ban"; 270 | "id" => user_id, "query" => delete_ban); 271 | self.conn.query(delete_ban, &[&user_id])?.pop(); 272 | 273 | Ok(()) 274 | } 275 | //endregion 276 | 277 | //region Antiflood 278 | pub fn get_antiflood(&mut self, token_id: i32) -> Result { 279 | let get_ban = "SELECT (banlist_all) FROM antiflood WHERE token = $1;"; 280 | debug!(utils::LOGGER, "Getting token antiflood settings"; 281 | "token" => token_id, "query" => get_ban); 282 | let row: Option = self.conn.query(get_ban, &[&token_id])?.pop(); 283 | 284 | Ok(match row { 285 | Some(antiflood) => Antiflood { 286 | banlist_all: antiflood.get(0), 287 | }, 288 | None => Antiflood::default(), 289 | }) 290 | } 291 | 292 | pub fn set_antiflood_banlist_all(&mut self, token_id: i32, time: NaiveDateTime) -> Result<(), postgres::Error> { 293 | let upsert_antiflood = " 294 | INSERT INTO antiflood (token, banlist_all) 295 | VALUES ($1, $2) 296 | ON CONFLICT (token) DO 297 | UPDATE SET banlist_all=EXCLUDED.banlist_all;"; 298 | debug!(utils::LOGGER, "Updating antiflood"; 299 | "token" => &token_id, "column" => "banlist_all", "query" => upsert_antiflood); 300 | self.conn.query(upsert_antiflood, &[&token_id, &time])?; 301 | Ok(()) 302 | } 303 | //endregion 304 | } 305 | -------------------------------------------------------------------------------- /src/errors.rs: -------------------------------------------------------------------------------- 1 | use std::fmt; 2 | 3 | use actix_web::error; 4 | use actix_web::http::StatusCode; 5 | use actix_web::HttpResponse; 6 | use failure::Fail; 7 | use postgres; 8 | use serde_json::{json, Value}; 9 | 10 | use crate::utils; 11 | 12 | #[derive(Fail, Debug)] 13 | pub enum UserError { 14 | Internal, 15 | NotFound, 16 | BadRequest(&'static str), 17 | MethodNotAllowed, 18 | Unauthorized, 19 | Forbidden, 20 | TooManyRequests { 21 | until: i64, 22 | }, 23 | } 24 | 25 | impl From for UserError { 26 | fn from(item: postgres::Error) -> Self { 27 | error!(utils::LOGGER, "{}", item); 28 | UserError::Internal 29 | } 30 | } 31 | 32 | impl From for UserError { 33 | fn from(item: serde_json::error::Error) -> Self { 34 | error!(utils::LOGGER, "{}", item); 35 | UserError::Internal 36 | } 37 | } 38 | 39 | impl fmt::Display for UserError { 40 | fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { 41 | write!(f, "Display: {}", self.to_json()) 42 | } 43 | } 44 | 45 | impl error::ResponseError for UserError { 46 | fn error_response(&self) -> HttpResponse { 47 | self.to_response() 48 | } 49 | 50 | fn render_response(&self) -> HttpResponse { 51 | self.to_response() 52 | } 53 | } 54 | 55 | impl UserError { 56 | fn to_json(&self) -> Value { 57 | match *self { 58 | UserError::Internal => json!({ 59 | "code": StatusCode::INTERNAL_SERVER_ERROR.as_u16(), 60 | "error": StatusCode::INTERNAL_SERVER_ERROR.canonical_reason() 61 | }), 62 | UserError::NotFound => json!({ 63 | "code": StatusCode::NOT_FOUND.as_u16(), 64 | "error": StatusCode::NOT_FOUND.canonical_reason() 65 | }), 66 | UserError::BadRequest(reason) => json!({ 67 | "code": StatusCode::BAD_REQUEST.as_u16(), 68 | "error": StatusCode::BAD_REQUEST.canonical_reason(), 69 | "reason": reason 70 | }), 71 | UserError::MethodNotAllowed => json!({ 72 | "code": StatusCode::METHOD_NOT_ALLOWED.as_u16(), 73 | "error": StatusCode::METHOD_NOT_ALLOWED.canonical_reason() 74 | }), 75 | UserError::Unauthorized => json!({ 76 | "code": StatusCode::UNAUTHORIZED.as_u16(), 77 | "error": StatusCode::UNAUTHORIZED.canonical_reason() 78 | }), 79 | UserError::Forbidden => json!({ 80 | "code": StatusCode::FORBIDDEN.as_u16(), 81 | "error": StatusCode::FORBIDDEN.canonical_reason() 82 | }), 83 | UserError::TooManyRequests { until } => json!({ 84 | "code": StatusCode::TOO_MANY_REQUESTS.as_u16(), 85 | "error": StatusCode::TOO_MANY_REQUESTS.canonical_reason(), 86 | "until": until 87 | }), 88 | } 89 | } 90 | 91 | pub fn to_response(&self) -> HttpResponse { 92 | match *self { 93 | UserError::Internal => HttpResponse::InternalServerError().json(self.to_json()), 94 | UserError::NotFound => HttpResponse::NotFound().json(self.to_json()), 95 | UserError::BadRequest(_) => HttpResponse::BadRequest().json(self.to_json()), 96 | UserError::MethodNotAllowed => HttpResponse::MethodNotAllowed().json(self.to_json()), 97 | UserError::Unauthorized => HttpResponse::Unauthorized().json(self.to_json()), 98 | UserError::Forbidden => HttpResponse::Forbidden().json(self.to_json()), 99 | UserError::TooManyRequests { until: _ } => HttpResponse::TooManyRequests().json(self.to_json()), 100 | } 101 | } 102 | } 103 | -------------------------------------------------------------------------------- /src/guards.rs: -------------------------------------------------------------------------------- 1 | use chrono::{Duration, NaiveDateTime, Utc}; 2 | use postgres_types::{FromSql, ToSql}; 3 | use serde::{Deserialize, Serialize}; 4 | 5 | use crate::database::{Antiflood, Database}; 6 | use crate::database::Token; 7 | use crate::errors::UserError; 8 | 9 | #[derive(Debug, ToSql, FromSql, Serialize, Deserialize)] 10 | #[postgres(name = "permission")] 11 | pub enum Permission { 12 | // Can read from the API 13 | User, 14 | // Can add IDs to the API 15 | Admin, 16 | // Can create/revoke tokens 17 | Root, 18 | } 19 | 20 | 21 | pub struct TokenGuard { 22 | pub token: Token, 23 | db: Database, 24 | antiflood: Antiflood, 25 | } 26 | 27 | impl TokenGuard { 28 | pub fn new(token_header: String) -> Result { 29 | let mut db = Database::new()?; 30 | if !token_header.is_empty() { 31 | let token = match db.get_token(token_header)? { 32 | Some(token) => token, 33 | None => return Err(UserError::Unauthorized), 34 | }; 35 | let antiflood = db.get_antiflood(token.id)?; 36 | 37 | if token.retired { 38 | return Err(UserError::Unauthorized); 39 | } 40 | 41 | Ok(TokenGuard { token, db, antiflood }) 42 | } else { 43 | return Err(UserError::Unauthorized); 44 | } 45 | } 46 | 47 | pub fn admin(&self) -> bool { 48 | match self.token.permission { 49 | Permission::Admin => true, 50 | Permission::Root => true, 51 | _ => false, 52 | } 53 | } 54 | 55 | pub fn root(&self) -> bool { 56 | match self.token.permission { 57 | Permission::Root => true, 58 | _ => false, 59 | } 60 | } 61 | 62 | pub fn banlist_all(&mut self) -> Result<(), UserError> { 63 | if self.admin() { 64 | return Ok(()); 65 | } 66 | let current_time = NaiveDateTime::from_timestamp(Utc::now().timestamp(), 0); 67 | if self.antiflood.banlist_all < current_time { 68 | self.db.set_antiflood_banlist_all(self.token.id, 69 | current_time + Duration::minutes(5))?; 70 | Ok(()) 71 | } else { 72 | return Err(UserError::TooManyRequests { until: self.antiflood.banlist_all.timestamp() }); 73 | } 74 | } 75 | } 76 | -------------------------------------------------------------------------------- /src/main.rs: -------------------------------------------------------------------------------- 1 | extern crate postgres; 2 | #[macro_use] 3 | extern crate slog; 4 | 5 | use std::process::exit; 6 | 7 | use actix_web::{App, HttpServer, web}; 8 | 9 | use crate::database::Database; 10 | use crate::errors::UserError; 11 | 12 | #[macro_use] 13 | mod utils; 14 | mod database; 15 | mod errors; 16 | mod guards; 17 | mod routes; 18 | mod settings; 19 | #[cfg(test)] 20 | mod tests; 21 | 22 | fn setup_database() -> Result { 23 | let mut db = match Database::new() { 24 | Ok(d) => d, 25 | Err(e) => { 26 | error!(utils::LOGGER, "A Error occured while connecting to PostgreSQL"; "error" => e.to_string()); 27 | return Ok(1); 28 | } 29 | }; 30 | db.create_genesis_token()?; 31 | Ok(0) 32 | } 33 | 34 | fn run() -> Result { 35 | info!(utils::LOGGER, "Starting {}", env!("CARGO_PKG_NAME"); "version" => &env!("CARGO_PKG_VERSION")); 36 | if settings::ENV.general.masterid == 777000 { 37 | warn!(utils::LOGGER, "MasterID not set. Defaulting to Telegrams id (777000). To avoid this set `masterid` under the `general` section in the config.") 38 | } 39 | info!( 40 | utils::LOGGER, 41 | "Master ID is {}", 42 | settings::ENV.general.masterid 43 | ); 44 | let db_code = setup_database()?; 45 | if db_code > 0 { 46 | return Ok(db_code); 47 | } 48 | let location = format!( 49 | "{}:{}", 50 | settings::ENV.server.host, 51 | settings::ENV.server.port 52 | ); 53 | info!(utils::LOGGER, "Starting Server on {}", location); 54 | HttpServer::new(|| { 55 | App::new() 56 | .default_service(web::route().to(|| UserError::NotFound.to_response())) 57 | .service( 58 | web::resource("/") 59 | .route(web::get().to(routes::root::info)) 60 | .route(web::head().to(routes::root::info)), 61 | ) 62 | .service(web::resource("/version").route(web::get().to(routes::root::version))) 63 | .service(web::resource("/stats").route(web::get().to(routes::root::stats))) 64 | .service( 65 | web::resource("/tokens") 66 | .route(web::get().to(routes::tokens::get_tokens)) 67 | .route(web::post().to(routes::tokens::post_tokens)), 68 | ) 69 | .service( 70 | web::resource("/tokens/{id}") 71 | .route(web::get().to(routes::tokens::get_token)) 72 | .route(web::delete().to(routes::tokens::delete_token)), 73 | ) 74 | .service( 75 | web::resource("/tokens/userid/{uid}") 76 | .route(web::get().to(routes::tokens::get_token_by_userid)) 77 | ) 78 | .service( 79 | web::resource("/banlist") 80 | .route(web::get().to(routes::banlist::get_bans)) 81 | .route(web::post().to(routes::banlist::post_bans)), 82 | ) 83 | .service( 84 | web::resource("/banlist/all") 85 | .route(web::get().to(routes::banlist::get_bans_id_list)) 86 | ) 87 | .service( 88 | web::resource("/banlist/{id}") 89 | .route(web::get().to(routes::banlist::get_ban)) 90 | .route(web::delete().to(routes::banlist::delete_ban)), 91 | ) 92 | }) 93 | .bind(location) 94 | .unwrap() 95 | .run() 96 | .unwrap(); 97 | Ok(0) 98 | } 99 | 100 | fn main() -> Result<(), postgres::Error> { 101 | let exit_code = run()?; 102 | exit(exit_code); 103 | } 104 | -------------------------------------------------------------------------------- /src/routes/banlist.rs: -------------------------------------------------------------------------------- 1 | use actix_web::{HttpRequest, HttpResponse, Result, web}; 2 | use serde::Deserialize; 3 | use serde_json::Value; 4 | 5 | use crate::database::Database; 6 | use crate::errors::UserError; 7 | use crate::guards::TokenGuard; 8 | use crate::utils; 9 | 10 | #[derive(Debug, Deserialize)] 11 | pub struct CreateBan { 12 | id: i64, 13 | reason: String, 14 | message: Option, 15 | } 16 | 17 | pub fn get_bans(req: HttpRequest) -> Result { 18 | let guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 19 | if guard.root() { 20 | let mut db = Database::new()?; 21 | let bans = db.get_bans()?; 22 | let nicer_bans: Vec = bans 23 | .iter() 24 | .map(|ban| ban.raw_json()) 25 | .collect(); 26 | let bans_json = serde_json::to_value(nicer_bans).map_err(|e| { 27 | error!(utils::LOGGER, "{}", e); 28 | UserError::Internal 29 | })?; 30 | 31 | Ok(HttpResponse::Ok().json(bans_json)) 32 | } else { 33 | Err(UserError::Forbidden) 34 | } 35 | } 36 | 37 | pub fn post_bans( 38 | req: HttpRequest, 39 | data: web::Json>, 40 | ) -> Result { 41 | let guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 42 | if guard.admin() { 43 | let mut db = Database::new()?; 44 | for ban in data.iter() { 45 | if !ban.reason.is_empty() { 46 | db.add_ban(ban.id, 47 | &ban.reason, 48 | guard.token.id, 49 | &ban.message)?; 50 | } else { 51 | return Err(UserError::BadRequest("ban reason can not be empty")); 52 | } 53 | } 54 | Ok(HttpResponse::NoContent().body("")) 55 | } else { 56 | Err(UserError::Forbidden) 57 | } 58 | } 59 | 60 | pub fn get_ban(req: HttpRequest) -> Result { 61 | let _guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 62 | let user_id: i64 = req.match_info().get("id").unwrap().parse().map_err(|_| { 63 | UserError::BadRequest("could not convert user id to integer") 64 | })?; 65 | let mut db = Database::new()?; 66 | match db.get_ban(user_id)? { 67 | Some(ban) => Ok(HttpResponse::Ok().json(ban.json()?)), 68 | None => Err(UserError::NotFound), 69 | } 70 | } 71 | 72 | pub fn delete_ban(req: HttpRequest) -> Result { 73 | let guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 74 | if guard.admin() { 75 | let user_id: i64 = req.match_info().get("id").unwrap().parse().map_err(|_| { 76 | UserError::BadRequest("could not convert id to integer") 77 | })?; 78 | 79 | let mut db = Database::new()?; 80 | 81 | match db.get_ban(user_id)? { 82 | Some(_) => { 83 | db.delete_ban(user_id)?; 84 | Ok(HttpResponse::NoContent().body("")) 85 | } 86 | None => Err(UserError::NotFound), 87 | } 88 | } else { 89 | Err(UserError::Forbidden) 90 | } 91 | } 92 | 93 | pub fn get_bans_id_list(req: HttpRequest) -> Result { 94 | let mut guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 95 | guard.banlist_all()?; 96 | let mut db = Database::new()?; 97 | let bans = db.get_banned_ids()?; 98 | let nicer_bans: Vec<&i64> = bans 99 | .iter() 100 | .collect(); 101 | let response: Vec = nicer_bans.iter().map(|i| i.to_string()).collect(); 102 | 103 | Ok(HttpResponse::Ok().body(response.join("\n"))) 104 | } 105 | -------------------------------------------------------------------------------- /src/routes/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod banlist; 2 | pub mod root; 3 | pub mod tokens; 4 | -------------------------------------------------------------------------------- /src/routes/root.rs: -------------------------------------------------------------------------------- 1 | use actix_web::{HttpRequest, HttpResponse}; 2 | use serde_json::json; 3 | 4 | use crate::settings; 5 | use crate::database::Database; 6 | use crate::errors::UserError; 7 | 8 | fn safe_href(name: &str, url: &str) -> String { 9 | format!(r#"{}"#, url, name) 10 | } 11 | 12 | pub fn info() -> HttpResponse { 13 | let staging_prefix = if settings::ENV.general.staging { 14 | "

Staging Instance. This is not the real API.

" 15 | } else { 16 | "" 17 | }; 18 | let body = format!( 19 | " 20 | 21 | {} 22 | {} v{} by {}
{}

{}
{}
{}
{}", 23 | staging_prefix, 24 | &env!("CARGO_PKG_NAME"), 25 | &env!("CARGO_PKG_VERSION"), 26 | &env!("CARGO_PKG_AUTHORS"), 27 | &env!("CARGO_PKG_DESCRIPTION"), 28 | safe_href("GitHub", &env!("CARGO_PKG_REPOSITORY")), 29 | safe_href("Channel", "https://t.me/SpamWatch"), 30 | safe_href("Documentation", "https://docs.spamwat.ch"), 31 | safe_href("Get an access token", "https://t.me/SpamWatchBot?start=token") 32 | ); 33 | HttpResponse::Ok().content_type("text/html").body(body) 34 | } 35 | 36 | pub fn version() -> HttpResponse { 37 | HttpResponse::Ok().json(json!({ 38 | "version": &env!("CARGO_PKG_VERSION"), 39 | "major": &env!("CARGO_PKG_VERSION_MAJOR"), 40 | "minor": &env!("CARGO_PKG_VERSION_MINOR"), 41 | "patch": &env!("CARGO_PKG_VERSION_PATCH") 42 | })) 43 | } 44 | 45 | pub fn stats(_req: HttpRequest) -> Result { 46 | let mut db = Database::new()?; 47 | let total_ban_count = db.get_total_ban_count()?; 48 | let stats = json!({ 49 | "total_ban_count": total_ban_count 50 | }); 51 | Ok(HttpResponse::Ok().json(serde_json::to_value(stats)?)) 52 | } 53 | -------------------------------------------------------------------------------- /src/routes/tokens.rs: -------------------------------------------------------------------------------- 1 | use actix_web::{HttpRequest, HttpResponse, Result, web}; 2 | use serde::Deserialize; 3 | 4 | use crate::database::Database; 5 | use crate::errors::UserError; 6 | use crate::guards::{Permission, TokenGuard}; 7 | use crate::utils; 8 | 9 | #[derive(Debug, Deserialize)] 10 | pub struct CreateToken { 11 | id: i64, 12 | permission: Permission, 13 | } 14 | 15 | pub fn get_tokens(req: HttpRequest) -> Result { 16 | let guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 17 | if guard.root() { 18 | let mut db = Database::new()?; 19 | let tokens = db.get_tokens()?; 20 | let tokens_json = serde_json::to_value(tokens).map_err(|e| { 21 | error!(utils::LOGGER, "{}", e); 22 | UserError::Internal 23 | })?; 24 | 25 | Ok(HttpResponse::Ok().json(tokens_json)) 26 | } else { 27 | Err(UserError::Forbidden) 28 | } 29 | } 30 | 31 | pub fn post_tokens( 32 | req: HttpRequest, 33 | data: web::Json, 34 | ) -> Result { 35 | let guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 36 | if guard.root() { 37 | let mut db = Database::new()?; 38 | let token = db.create_token(&data.permission, data.id)?; 39 | match db.get_token(token)? { 40 | Some(token) => Ok(HttpResponse::Created().json(token.json()?)), 41 | None => Err(UserError::NotFound), 42 | } 43 | } else { 44 | Err(UserError::Forbidden) 45 | } 46 | } 47 | 48 | pub fn get_token(req: HttpRequest) -> Result { 49 | let guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 50 | 51 | let mut db = Database::new()?; 52 | let _id = req.match_info().get("id").unwrap(); 53 | if _id == "self" { 54 | match db.get_token(utils::get_auth_token(&req)?)? { 55 | Some(token) => Ok(HttpResponse::Ok().json(token.json()?)), 56 | None => Err(UserError::NotFound), 57 | } 58 | } else { 59 | if guard.root() { 60 | let token_id: i32 = _id.parse().map_err(|_| { 61 | UserError::BadRequest("could not convert token id to integer") 62 | })?; 63 | match db.get_token_by_id(token_id)? { 64 | Some(token) => Ok(HttpResponse::Ok().json(token.json()?)), 65 | None => Err(UserError::NotFound), 66 | } 67 | } else { 68 | Err(UserError::Forbidden) 69 | } 70 | } 71 | } 72 | 73 | pub fn get_token_by_userid(req: HttpRequest) -> Result { 74 | let guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 75 | 76 | let mut db = Database::new()?; 77 | let uid = req.match_info().get("uid").unwrap(); 78 | 79 | if guard.root() { 80 | let uid: i64 = uid.parse().map_err(|_| { 81 | UserError::BadRequest("could not convert user id to integer") 82 | })?; 83 | let tokens = db.get_token_by_userid(uid)?; 84 | let tokens_json = serde_json::to_value(tokens).map_err(|e| { 85 | error!(utils::LOGGER, "{}", e); 86 | UserError::Internal 87 | })?; 88 | 89 | Ok(HttpResponse::Ok().json(tokens_json)) 90 | } else { 91 | Err(UserError::Forbidden) 92 | } 93 | } 94 | 95 | pub fn delete_token(req: HttpRequest) -> Result { 96 | let guard = TokenGuard::new(utils::get_auth_token(&req)?)?; 97 | 98 | if guard.root() { 99 | let mut db = Database::new()?; 100 | let token_id: i32 = req.match_info().get("id").unwrap().parse().map_err(|_| { 101 | UserError::BadRequest("could not convert token id to integer") 102 | })?; 103 | match db.get_token_by_id(token_id)? { 104 | Some(_token) => { 105 | db.revoke_token_by_id(token_id)?; 106 | Ok(HttpResponse::NoContent().body("")) 107 | } 108 | None => Err(UserError::NotFound), 109 | } 110 | } else { 111 | Err(UserError::Forbidden) 112 | } 113 | } 114 | -------------------------------------------------------------------------------- /src/settings.rs: -------------------------------------------------------------------------------- 1 | use std::path::PathBuf; 2 | 3 | use config::{Config, ConfigError, Environment, File}; 4 | use dirs::home_dir; 5 | use lazy_static::lazy_static; 6 | use serde::{Deserialize, Serialize}; 7 | 8 | use crate::utils; 9 | 10 | lazy_static! { 11 | pub static ref ENV: Settings = match Settings::load() { 12 | Ok(settings) => { 13 | debug!(utils::LOGGER, "Settings:"; "name" => &settings.database.name); 14 | settings 15 | } 16 | Err(err) => { 17 | error!(utils::LOGGER, "{}", &format!("{}", err)); 18 | Settings::default() 19 | } 20 | }; 21 | } 22 | 23 | #[derive(Debug, Serialize, Deserialize)] 24 | pub struct General { 25 | pub masterid: i64, 26 | pub token_size: u8, 27 | pub staging: bool, 28 | } 29 | 30 | #[derive(Debug, Serialize, Deserialize)] 31 | pub struct DatabaseCfg { 32 | pub host: String, 33 | pub port: u16, 34 | pub name: String, 35 | pub username: String, 36 | pub password: String, 37 | } 38 | 39 | #[derive(Debug, Serialize, Deserialize)] 40 | pub struct ServerCfg { 41 | pub host: String, 42 | pub port: u16, 43 | } 44 | 45 | #[derive(Debug, Serialize, Deserialize)] 46 | pub struct Settings { 47 | pub database: DatabaseCfg, 48 | pub server: ServerCfg, 49 | pub general: General, 50 | } 51 | 52 | impl Default for Settings { 53 | fn default() -> Self { 54 | Settings { 55 | database: DatabaseCfg { 56 | host: "127.0.0.1".to_string(), 57 | port: 5432, 58 | name: "SpamWatchAPI".to_string(), 59 | username: "SpamWatchAPI".to_string(), 60 | password: String::default(), 61 | }, 62 | server: ServerCfg { 63 | host: "127.0.0.1".to_string(), 64 | port: 6345, 65 | }, 66 | general: General { 67 | masterid: 777000, 68 | token_size: 64, 69 | staging: false, 70 | }, 71 | } 72 | } 73 | } 74 | 75 | impl Settings { 76 | pub fn load() -> Result { 77 | let home_config: PathBuf = match home_dir() { 78 | Some(path) => [ 79 | path, 80 | PathBuf::from(&format!(".config/{}/config", &env!("CARGO_PKG_NAME"))), 81 | ] 82 | .iter() 83 | .collect(), 84 | None => { 85 | debug!(utils::LOGGER, "Can't get home directory"); 86 | PathBuf::from("config") 87 | } 88 | }; 89 | 90 | let defaults = Config::try_from(&Settings::default())?; 91 | let mut settings = Config::default(); 92 | settings.merge(defaults)?; 93 | settings 94 | .merge( 95 | File::with_name(&format!("/etc/{}/config", &env!("CARGO_PKG_NAME"))) 96 | .required(false), 97 | )? 98 | .merge(File::with_name(home_config.to_str().unwrap()).required(false))? 99 | .merge(File::with_name("config").required(false))? 100 | .merge(Environment::with_prefix("APP"))?; 101 | 102 | Ok(settings.try_into().unwrap()) 103 | } 104 | } 105 | -------------------------------------------------------------------------------- /src/tests/mod.rs: -------------------------------------------------------------------------------- 1 | mod root; 2 | mod tokens; 3 | -------------------------------------------------------------------------------- /src/tests/root.rs: -------------------------------------------------------------------------------- 1 | #[cfg(test)] 2 | mod get { 3 | use actix_service::Service; 4 | use actix_web::{App, guard, HttpResponse, web}; 5 | use actix_web::http::StatusCode; 6 | use actix_web::test; 7 | 8 | use crate::routes; 9 | 10 | #[test] 11 | fn test_version() { 12 | let mut app = test::init_service( 13 | App::new().service( 14 | web::resource("/version").route( 15 | web::route() 16 | .guard(guard::Get()) 17 | .to(|| HttpResponse::MethodNotAllowed()) 18 | .to(routes::root::version), 19 | ), 20 | ), 21 | ); 22 | // Create request object 23 | let req = test::TestRequest::get().uri("/version").to_request(); 24 | 25 | // Execute application 26 | let resp = test::block_on(app.call(req)).unwrap(); 27 | assert_eq!(resp.status(), StatusCode::OK); 28 | } 29 | } 30 | 31 | #[cfg(test)] 32 | mod post { 33 | use actix_service::Service; 34 | use actix_web::{App, guard, HttpResponse, web}; 35 | use actix_web::http::StatusCode; 36 | use actix_web::test; 37 | 38 | use crate::routes; 39 | 40 | #[test] 41 | fn test_version() { 42 | let mut app = test::init_service( 43 | App::new().service( 44 | web::resource("/version").route( 45 | web::route() 46 | .guard(guard::Get()) 47 | .to(|| HttpResponse::MethodNotAllowed()) 48 | .to(routes::root::version), 49 | ), 50 | ), 51 | ); 52 | // Create request object 53 | let req = test::TestRequest::post().uri("/version").to_request(); 54 | 55 | // Execute application 56 | let resp = test::block_on(app.call(req)).unwrap(); 57 | assert_eq!(resp.status(), StatusCode::METHOD_NOT_ALLOWED); 58 | } 59 | } 60 | 61 | #[cfg(test)] 62 | mod put { 63 | use actix_service::Service; 64 | use actix_web::{App, guard, HttpResponse, web}; 65 | use actix_web::http::StatusCode; 66 | use actix_web::test; 67 | 68 | use crate::routes; 69 | 70 | #[test] 71 | fn test_version() { 72 | let mut app = test::init_service( 73 | App::new().service( 74 | web::resource("/version").route( 75 | web::route() 76 | .guard(guard::Get()) 77 | .to(|| HttpResponse::MethodNotAllowed()) 78 | .to(routes::root::version), 79 | ), 80 | ), 81 | ); 82 | // Create request object 83 | let req = test::TestRequest::put().uri("/version").to_request(); 84 | 85 | // Execute application 86 | let resp = test::block_on(app.call(req)).unwrap(); 87 | assert_eq!(resp.status(), StatusCode::METHOD_NOT_ALLOWED); 88 | } 89 | } 90 | 91 | #[cfg(test)] 92 | mod patch { 93 | use actix_service::Service; 94 | use actix_web::{App, guard, HttpResponse, web}; 95 | use actix_web::http::StatusCode; 96 | use actix_web::test; 97 | 98 | use crate::routes; 99 | 100 | #[test] 101 | fn test_version() { 102 | let mut app = test::init_service( 103 | App::new().service( 104 | web::resource("/version").route( 105 | web::route() 106 | .guard(guard::Get()) 107 | .to(|| HttpResponse::MethodNotAllowed()) 108 | .to(routes::root::version), 109 | ), 110 | ), 111 | ); 112 | // Create request object 113 | let req = test::TestRequest::patch().uri("/version").to_request(); 114 | 115 | // Execute application 116 | let resp = test::block_on(app.call(req)).unwrap(); 117 | assert_eq!(resp.status(), StatusCode::METHOD_NOT_ALLOWED); 118 | } 119 | } 120 | 121 | #[cfg(test)] 122 | mod delete { 123 | use actix_service::Service; 124 | use actix_web::{App, guard, HttpResponse, web}; 125 | use actix_web::http::StatusCode; 126 | use actix_web::test; 127 | 128 | use crate::routes; 129 | 130 | #[test] 131 | fn test_version() { 132 | let mut app = test::init_service( 133 | App::new().service( 134 | web::resource("/version").route( 135 | web::route() 136 | .guard(guard::Get()) 137 | .to(|| HttpResponse::MethodNotAllowed()) 138 | .to(routes::root::version), 139 | ), 140 | ), 141 | ); 142 | // Create request object 143 | let req = test::TestRequest::delete().uri("/version").to_request(); 144 | 145 | // Execute application 146 | let resp = test::block_on(app.call(req)).unwrap(); 147 | assert_eq!(resp.status(), StatusCode::METHOD_NOT_ALLOWED); 148 | } 149 | } 150 | -------------------------------------------------------------------------------- /src/tests/tokens.rs: -------------------------------------------------------------------------------- 1 | #[cfg(test)] 2 | mod get { 3 | use actix_service::Service; 4 | use actix_web::{App, guard, HttpResponse, web}; 5 | use actix_web::http::StatusCode; 6 | use actix_web::test; 7 | 8 | use crate::routes; 9 | 10 | #[test] 11 | fn test_tokens_no_auth() { 12 | let mut app = test::init_service( 13 | App::new().service( 14 | web::resource("/tokens").route( 15 | web::route() 16 | .guard(guard::Get()) 17 | .to(|| HttpResponse::MethodNotAllowed()) 18 | .to(routes::tokens::get_tokens), 19 | ), 20 | ), 21 | ); 22 | // Create request object 23 | let req = test::TestRequest::get().uri("/tokens").to_request(); 24 | 25 | // Execute application 26 | let resp = test::block_on(app.call(req)).unwrap(); 27 | assert_eq!(resp.status(), StatusCode::FORBIDDEN); 28 | } 29 | 30 | #[test] 31 | fn test_token_no_auth() { 32 | let mut app = test::init_service( 33 | App::new().service( 34 | web::resource("/tokens/{id}").route( 35 | web::route() 36 | .guard(guard::Get()) 37 | .to(|| HttpResponse::MethodNotAllowed()) 38 | .to(routes::tokens::get_tokens), 39 | ), 40 | ), 41 | ); 42 | // Create request object 43 | let req = test::TestRequest::get().uri("/tokens/1").to_request(); 44 | 45 | // Execute application 46 | let resp = test::block_on(app.call(req)).unwrap(); 47 | assert_eq!(resp.status(), StatusCode::FORBIDDEN); 48 | } 49 | } 50 | 51 | #[cfg(test)] 52 | mod post { 53 | use actix_service::Service; 54 | use actix_web::{App, guard, HttpResponse, web}; 55 | use actix_web::http::StatusCode; 56 | use actix_web::test; 57 | 58 | use crate::routes; 59 | 60 | #[test] 61 | fn test_version() { 62 | let mut app = test::init_service( 63 | App::new().service( 64 | web::resource("/tokens").route( 65 | web::route() 66 | .guard(guard::Post()) 67 | .to(|| HttpResponse::MethodNotAllowed()) 68 | .to(routes::root::version), 69 | ), 70 | ), 71 | ); 72 | // Create request object 73 | let req = test::TestRequest::post().uri("/tokens").to_request(); 74 | 75 | // Execute application 76 | let resp = test::block_on(app.call(req)).unwrap(); 77 | assert_eq!(resp.status(), StatusCode::METHOD_NOT_ALLOWED); 78 | } 79 | } 80 | 81 | #[cfg(test)] 82 | mod put { 83 | use actix_service::Service; 84 | use actix_web::{App, guard, HttpResponse, web}; 85 | use actix_web::http::StatusCode; 86 | use actix_web::test; 87 | 88 | use crate::routes; 89 | 90 | #[test] 91 | fn test_version() { 92 | let mut app = test::init_service( 93 | App::new().service( 94 | web::resource("/version").route( 95 | web::route() 96 | .guard(guard::Get()) 97 | .to(|| HttpResponse::MethodNotAllowed()) 98 | .to(routes::root::version), 99 | ), 100 | ), 101 | ); 102 | // Create request object 103 | let req = test::TestRequest::put().uri("/version").to_request(); 104 | 105 | // Execute application 106 | let resp = test::block_on(app.call(req)).unwrap(); 107 | assert_eq!(resp.status(), StatusCode::METHOD_NOT_ALLOWED); 108 | } 109 | } 110 | 111 | #[cfg(test)] 112 | mod patch { 113 | use actix_service::Service; 114 | use actix_web::{App, guard, HttpResponse, web}; 115 | use actix_web::http::StatusCode; 116 | use actix_web::test; 117 | 118 | use crate::routes; 119 | 120 | #[test] 121 | fn test_version() { 122 | let mut app = test::init_service( 123 | App::new().service( 124 | web::resource("/version").route( 125 | web::route() 126 | .guard(guard::Get()) 127 | .to(|| HttpResponse::MethodNotAllowed()) 128 | .to(routes::root::version), 129 | ), 130 | ), 131 | ); 132 | // Create request object 133 | let req = test::TestRequest::patch().uri("/version").to_request(); 134 | 135 | // Execute application 136 | let resp = test::block_on(app.call(req)).unwrap(); 137 | assert_eq!(resp.status(), StatusCode::METHOD_NOT_ALLOWED); 138 | } 139 | } 140 | 141 | #[cfg(test)] 142 | mod delete { 143 | use actix_service::Service; 144 | use actix_web::{App, guard, HttpResponse, web}; 145 | use actix_web::http::StatusCode; 146 | use actix_web::test; 147 | 148 | use crate::routes; 149 | 150 | #[test] 151 | fn test_version() { 152 | let mut app = test::init_service( 153 | App::new().service( 154 | web::resource("/version").route( 155 | web::route() 156 | .guard(guard::Get()) 157 | .to(|| HttpResponse::MethodNotAllowed()) 158 | .to(routes::root::version), 159 | ), 160 | ), 161 | ); 162 | // Create request object 163 | let req = test::TestRequest::delete().uri("/version").to_request(); 164 | 165 | // Execute application 166 | let resp = test::block_on(app.call(req)).unwrap(); 167 | assert_eq!(resp.status(), StatusCode::METHOD_NOT_ALLOWED); 168 | } 169 | } 170 | -------------------------------------------------------------------------------- /src/utils.rs: -------------------------------------------------------------------------------- 1 | use actix_web::HttpRequest; 2 | use lazy_static::lazy_static; 3 | use slog::{Drain, Logger}; 4 | use slog_async; 5 | use slog_term; 6 | 7 | use crate::errors::UserError; 8 | 9 | fn logger() -> Logger { 10 | let decorator = slog_term::TermDecorator::new().force_color().build(); 11 | let drain = slog_term::CompactFormat::new(decorator).build().fuse(); 12 | let drain = slog_async::Async::new(drain).build().fuse(); 13 | 14 | Logger::root(drain, o!()) 15 | } 16 | 17 | lazy_static! { 18 | pub static ref LOGGER: Logger = logger(); 19 | } 20 | 21 | pub fn get_auth_token(req: &HttpRequest) -> Result { 22 | let token_header = match req.headers().get("authorization") { 23 | Some(v) => v.to_str().map_err(|_| { 24 | UserError::BadRequest("could not convert token into string") 25 | })?, 26 | None => { 27 | return Err(UserError::Unauthorized); 28 | } 29 | }; 30 | let _token: Vec<&str> = token_header.split_ascii_whitespace().collect(); 31 | Ok(_token.get(1).ok_or(UserError::BadRequest("could not find token. is it prefixed with `Bearer` ?"))?.to_string()) 32 | } 33 | --------------------------------------------------------------------------------