1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
extern crate rustc_serialize;
extern crate chrono;
extern crate fractal_utils as utils;

use std::collections::{HashMap, BTreeSet};
use std::fmt;
use std::error::Error;
use rustc_serialize::{Encodable, Decodable};

use chrono::{NaiveDate, DateTime, UTC};
use utils::{Amount, WalletAddress, Address, Relationship};

/// Enum that represents
#[derive(Debug, PartialEq, Eq, Copy, Clone, RustcDecodable, RustcEncodable)]
pub enum ScopeDTO {
    /// Administration scope
    ///
    /// This scope is used for administration purposes, and will not be enabled for public
    /// development accounts.
    Admin,
    /// User scope
    ///
    /// This scope will provide access to user functionality, such as creating transactions and
    /// editing user information. It contains the user ID for which the token is valid.
    User(u64),
    /// Public scope
    ///
    /// This scope is the public scope. Every client will have access to everything provided in the
    /// admin scope.
    Public,
    /// Developer scope
    ///
    /// This scope is used for administration purposes, and will not be enabled for public
    /// development accounts.
    Developer,
}

impl fmt::Display for ScopeDTO {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{:?}", self)
    }
}



/// The user date type object
#[derive(RustcEncodable, RustcDecodable)]
pub struct UserDTO {
    /// The unique ID of the user
    pub id: u64,
    /// The unique username of the user
    pub username: String,
    /// The users email
    pub email: String,
    //// Whether the email has been confirmed or not
    pub email_confirmed: bool,
    /// The users first name
    pub first: Option<String>,
    /// Whether the first name has been confirmed or not
    pub first_confirmed: bool,
    /// The users last name
    pub last: Option<String>,
    /// Whether the last name has been confirmed
    pub last_confirmed: bool,
    /// The amount of devices the user has
    pub device_count: u8,
    /// The users wallet addresses
    pub wallet_addresses: BTreeSet<WalletAddress>,
    /// The users checking balance
    pub checking_balance: Amount,
    /// The users cold balance
    pub cold_balance: Amount,
    /// The users bonds and when he purchased them
    pub bonds: HashMap<DateTime<UTC>, u64>,
    /// The users birthday
    pub birthday: Option<NaiveDate>,
    /// Whether the birthday has been confirmed
    pub birthday_confirmed: bool,
    /// The users phone #
    pub phone: Option<String>,
    // Whether the users phone ## has been confirmed
    pub phone_confirmed: bool,
    /// The users profile picture
    pub image: Option<String>,
    /// The users address
    pub address: Option<Address>,
    /// Whether the address has been confirmed
    pub address_confirmed: bool,
    /// The users sybil score
    pub sybil_score: i8,
    /// The users trust score
    pub trust_score: i8,
    /// Whether the users account id disabled
    pub enabled: bool,
    /// When the user registered
    pub registered: DateTime<UTC>,
    /// The users last activity time
    pub last_activty: DateTime<UTC>,
    /// Whether the user is banned and until when
    pub banned: Option<DateTime<UTC>>,
}

impl DTO for UserDTO {}

/// The login date type object
#[derive(RustcEncodable, RustcDecodable)]
pub struct LoginDTO {
    /// The users username or email
    pub user_email: String,
    /// The users password
    pub password: String,
}

impl DTO for LoginDTO {}

/// Holds both public and signing keys encoded in base64
#[derive(RustcEncodable, RustcDecodable)]
pub struct PublicKeysDTO {
    pub public_sign_key: String,
    pub public_encrypt_key: String,
}

impl DTO for PublicKeysDTO {}

/// Struct for a fractal connection
#[derive(Clone, RustcEncodable, RustcDecodable)]
pub struct FractalConnectionDTO {
    /// Where the connection originated
    pub origin_id: u64,
    /// Who the user is trying to connect to
    pub destination_id: u64,
    /// The particulars of there relationship
    pub relationship: Relationship,
}

impl DTO for FractalConnectionDTO {}

/// Struct for for fractal developer client
#[derive(Clone, RustcEncodable, RustcDecodable)]
pub struct DeveloperClientDTO {
    /// The name of the client
    pub name: String,
    /// The permissions the client has
    pub scopes: Vec<ScopeDTO>,
}

impl DTO for DeveloperClientDTO {}

/// Struct to a confirm pending connection
#[derive(Clone, RustcEncodable, RustcDecodable)]
pub struct ConfirmPendingConnectionDTO {
    /// The id of the connection
    pub id: u64,
    /// Where the connection originated
    pub origin: u64,
    /// The user confirming the connection
    pub destination: u64,
}

impl DTO for ConfirmPendingConnectionDTO {}

/// Struct to reset the users password
#[derive(Clone, RustcEncodable, RustcDecodable)]
pub struct ResetPasswordDTO {
    /// The the username of the user
    pub username: String,
    /// Where the email of the user
    pub email: String,
}

impl DTO for ResetPasswordDTO {}


/// Struct used to update user information
#[derive(Clone, RustcEncodable, RustcDecodable)]
pub struct UpdateUserDTO {
    /// The users new username
    pub new_username: Option<String>,
    /// The users old password
    pub old_password: Option<String>,
    /// The users new password
    pub new_password: Option<String>,
    /// The users new first name
    pub new_first: Option<String>,
    /// The users new last name
    pub new_last: Option<String>,
    /// The users new address
    pub new_address: Option<Address>,
    /// The users new birthday
    pub new_birthday: Option<NaiveDate>,
    /// The users new phone #
    pub new_phone: Option<String>,
    /// The users new email
    pub new_email: Option<String>,
    /// The users new profile picture
    pub new_image: Option<String>,
}

impl DTO for UpdateUserDTO {}

/// Struct used to generate a transaction
#[derive(Clone, RustcEncodable, RustcDecodable)]
pub struct GenerateTransactionDTO {
    /// Where the transaction originated
    pub origin_id: u64,
    /// The destination wallet address of the transaction
    pub destination_address: WalletAddress,
    /// Who the transaction is going to
    pub destination_id: u64,
    /// The amount of the transaction
    pub amount: Amount,
}

impl DTO for GenerateTransactionDTO { }

/// Struct for for signup verification
#[derive(Clone, RustcEncodable, RustcDecodable)]
pub struct RegisterDTO {
    /// The users username
    pub username: String,
    /// The users password
    pub password: String,
    /// The users email
    pub email: String,
}

impl DTO for RegisterDTO { }

/// Response Data type object
#[derive(Debug, Clone, RustcDecodable, RustcEncodable)]
pub struct ResponseDTO {
    /// The message
    pub message: String,

}

impl ResponseDTO {

    pub fn new<S: AsRef<str>>(message: S) -> ResponseDTO {
        ResponseDTO {
            message: String::from(message.as_ref())
        }
    }

    pub fn set_message<S: AsRef<str>>(&mut self, message: S) {
        self.message = String::from(message.as_ref());
    }

}

impl DTO for ResponseDTO { }

/// AccessToken Data type object
#[derive(Debug, Clone, RustcDecodable, RustcEncodable)]
pub struct AccessTokenDTO {
    /// The app id
    pub app_id: String,
    /// The permissions of the access token
    pub scopes: String,
    /// The access token
    pub access_token: String,
    /// The access tokken type (currently only configured for bearer)
    pub token_type: TokenTypeDTO,
    /// The expiration time of the token
    pub expiration: i64,
}

impl DTO for AccessTokenDTO {}

/// Token type data type object (currently only using bearer)
#[derive(Debug, PartialEq, Eq, Copy, Clone, RustcDecodable, RustcEncodable)]
pub enum TokenTypeDTO {
    Bearer,
}

impl fmt::Display for TokenTypeDTO {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{:?}", self)
    }
}

impl DTO for TokenTypeDTO {}

pub trait DTO: Encodable + Decodable {}

pub trait FromDTO<D: DTO>: Sized {
    fn from_dto(dto: D) -> Result<Self, FromDTOError>;
}

#[derive(Debug)]
pub struct FromDTOError {
    error: String,
}

impl FromDTOError {
    /// Creates a new FromDTOError
    pub fn new<S: AsRef<str>>(error: S) -> FromDTOError {
        FromDTOError {
            error: String::from(error.as_ref()),
        }
    }
}

impl fmt::Display for FromDTOError {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{}", self.error)
    }
}

impl Error for FromDTOError {
    fn description(&self) -> &str {
        &self.error
    }

    fn cause(&self) -> Option<&Error> {
        None
    }
}