Compare commits
	
		
			2 Commits
		
	
	
		
			fa700c2315
			...
			d7da1824cf
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
| d7da1824cf | |||
| af83d5f733 | 
							
								
								
									
										103
									
								
								src/data.rs
									
									
									
									
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										103
									
								
								src/data.rs
									
									
									
									
									
								
							| @ -40,13 +40,16 @@ pub enum Error { | ||||
| 
 | ||||
|     #[error("Could not find contract {0}")] | ||||
|     AppContractNotFound(String), | ||||
| 
 | ||||
|     #[error("Could not find contract {0}")] | ||||
|     ContractNotFound(String), | ||||
| } | ||||
| 
 | ||||
| #[derive(Clone, Default, Serialize, Deserialize, Debug)] | ||||
| pub struct AccountData { | ||||
|     pub balance: u64, | ||||
|     pub tmp_locked: u64, | ||||
|     // holds reasons why VMs of this account got kicked
 | ||||
|     // holds reasons why Contracts of this account got kicked
 | ||||
|     pub kicked_for: Vec<String>, | ||||
|     pub last_kick: chrono::DateTime<Utc>, | ||||
|     // holds accounts that banned this account
 | ||||
| @ -247,7 +250,7 @@ impl From<AppContract> for AppContractPB { | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| #[derive(Eq, Hash, PartialEq, Clone, Debug, Default, Serialize, Deserialize)] | ||||
| #[derive(Eq, PartialEq, Clone, Debug, Default, Serialize, Deserialize)] | ||||
| pub struct AppNode { | ||||
|     pub node_pubkey: String, | ||||
|     pub operator_wallet: String, | ||||
| @ -262,7 +265,8 @@ pub struct AppNode { | ||||
|     pub max_ports_per_app: u32, | ||||
|     // nanotokens per unit per minute
 | ||||
|     pub price: u64, | ||||
| 
 | ||||
|     // 1st String is user wallet and 2nd String is report message
 | ||||
|     pub reports: HashMap<String, String>, | ||||
|     pub offline_minutes: u64, | ||||
| } | ||||
| 
 | ||||
| @ -506,7 +510,6 @@ impl BrainData { | ||||
|         nodes.push(node); | ||||
|     } | ||||
| 
 | ||||
|     // todo: this should also support Apps
 | ||||
|     /// Receives: operator, contract uuid, reason of kick
 | ||||
|     pub async fn kick_contract( | ||||
|         &self, | ||||
| @ -515,17 +518,46 @@ impl BrainData { | ||||
|         reason: &str, | ||||
|     ) -> Result<u64, Error> { | ||||
|         log::debug!("Operator {operator} requested a kick of {uuid} for reason: {reason}"); | ||||
|         let contract = self.find_contract_by_uuid(uuid)?; | ||||
| 
 | ||||
|         let (admin_pubkey, node_pubkey, updated_at, price_per_mint, is_vm) = | ||||
|             match self.find_any_contract_by_uuid(uuid) { | ||||
|                 Ok((Some(vm), _)) => { | ||||
|                     let price_per_mint = vm.price_per_minute(); | ||||
|                     ( | ||||
|                         vm.admin_pubkey, | ||||
|                         vm.node_pubkey, | ||||
|                         vm.updated_at, | ||||
|                         price_per_mint, | ||||
|                         true, | ||||
|                     ) | ||||
|                 } | ||||
|                 Ok((_, Some(app))) => { | ||||
|                     let price_per_mint = app.price_per_minute(); | ||||
| 
 | ||||
|                     ( | ||||
|                         app.admin_pubkey, | ||||
|                         app.node_pubkey, | ||||
|                         app.updated_at, | ||||
|                         price_per_mint, | ||||
|                         false, | ||||
|                     ) | ||||
|                 } | ||||
|                 _ => { | ||||
|                     log::error!("Could not find contract {uuid}"); | ||||
|                     return Err(Error::ContractNotFound(uuid.to_string())); | ||||
|                 } | ||||
|             }; | ||||
| 
 | ||||
|         let mut operator_data = self | ||||
|             .operators | ||||
|             .get_mut(operator) | ||||
|             .ok_or(Error::AccessDenied)?; | ||||
|         if !operator_data.vm_nodes.contains(&contract.node_pubkey) { | ||||
|         if !operator_data.vm_nodes.contains(&node_pubkey) { | ||||
|             return Err(Error::AccessDenied); | ||||
|         } | ||||
| 
 | ||||
|         let mut minutes_to_refund = chrono::Utc::now() | ||||
|             .signed_duration_since(contract.updated_at) | ||||
|             .signed_duration_since(updated_at) | ||||
|             .num_minutes() | ||||
|             .abs() as u64; | ||||
|         // cap refund at 1 week
 | ||||
| @ -533,10 +565,10 @@ impl BrainData { | ||||
|             minutes_to_refund = 10080; | ||||
|         } | ||||
| 
 | ||||
|         let mut refund_amount = minutes_to_refund * contract.price_per_minute(); | ||||
|         let mut refund_amount = minutes_to_refund * price_per_mint; | ||||
|         let mut admin_account = self | ||||
|             .accounts | ||||
|             .get_mut(&contract.admin_pubkey) | ||||
|             .get_mut(&admin_pubkey) | ||||
|             .ok_or(Error::ImpossibleError)?; | ||||
| 
 | ||||
|         // check if he got kicked within the last day
 | ||||
| @ -560,15 +592,22 @@ impl BrainData { | ||||
|         admin_account.kicked_for.push(reason.to_string()); | ||||
|         operator_data.escrow -= refund_amount; | ||||
| 
 | ||||
|         let admin_pubkey = contract.admin_pubkey.clone(); | ||||
|         let admin_pubkey = admin_pubkey.clone(); | ||||
|         drop(admin_account); | ||||
|         drop(contract); | ||||
| 
 | ||||
|         self.delete_vm(grpc::DeleteVmReq { | ||||
|             uuid: uuid.to_string(), | ||||
|             admin_pubkey, | ||||
|         }) | ||||
|         .await?; | ||||
|         if is_vm { | ||||
|             self.delete_vm(grpc::DeleteVmReq { | ||||
|                 uuid: uuid.to_string(), | ||||
|                 admin_pubkey, | ||||
|             }) | ||||
|             .await?; | ||||
|         } else { | ||||
|             self.send_del_container_req(DelAppReq { | ||||
|                 uuid: uuid.to_string(), | ||||
|                 admin_pubkey, | ||||
|             }) | ||||
|             .await?; | ||||
|         } | ||||
| 
 | ||||
|         Ok(refund_amount) | ||||
|     } | ||||
| @ -594,10 +633,15 @@ impl BrainData { | ||||
|             }); | ||||
|     } | ||||
| 
 | ||||
|     pub fn report_node(&self, admin_pubkey: String, node: &str, report: String) { | ||||
|         let mut nodes = self.vm_nodes.write().unwrap(); | ||||
|         if let Some(node) = nodes.iter_mut().find(|n| n.public_key == node) { | ||||
|             node.reports.insert(admin_pubkey, report); | ||||
|     pub fn report_any_node(&self, admin_pubkey: String, node: &str, report: String) { | ||||
|         let mut vm_nodes = self.vm_nodes.write().unwrap(); | ||||
|         if let Some(vm_node) = vm_nodes.iter_mut().find(|n| n.public_key == node) { | ||||
|             vm_node.reports.insert(admin_pubkey.clone(), report.clone()); | ||||
|         } | ||||
| 
 | ||||
|         let mut app_nodes = self.app_nodes.write().unwrap(); | ||||
|         if let Some(app_node) = app_nodes.iter_mut().find(|n| n.node_pubkey == node) { | ||||
|             app_node.reports.insert(admin_pubkey, report); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
| @ -1239,6 +1283,25 @@ impl BrainData { | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| impl BrainData { | ||||
|     pub fn find_any_contract_by_uuid( | ||||
|         &self, | ||||
|         uuid: &str, | ||||
|     ) -> Result<(Option<VmContract>, Option<AppContract>), Error> { | ||||
|         let contracts = self.vm_contracts.read().unwrap(); | ||||
|         if let Some(vm_contract) = contracts.iter().cloned().find(|c| c.uuid == uuid) { | ||||
|             return Ok((Some(vm_contract), None)); | ||||
|         } | ||||
| 
 | ||||
|         let app_contracts = self.app_contracts.read().unwrap(); | ||||
|         if let Some(app_contract) = app_contracts.iter().cloned().find(|c| c.uuid == uuid) { | ||||
|             return Ok((None, Some(app_contract))); | ||||
|         } | ||||
| 
 | ||||
|         Err(Error::ContractNotFound(uuid.to_string())) | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| impl BrainData { | ||||
|     pub fn add_app_daemon_tx(&self, node_pubkey: &str, tx: Sender<BrainMessageApp>) { | ||||
|         self.app_daemon_tx.insert(node_pubkey.to_string(), tx); | ||||
|  | ||||
							
								
								
									
										16
									
								
								src/grpc.rs
									
									
									
									
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										16
									
								
								src/grpc.rs
									
									
									
									
									
								
							| @ -99,17 +99,23 @@ impl BrainGeneralCli for BrainGeneraClilMock { | ||||
| 
 | ||||
|     async fn report_node(&self, req: Request<ReportNodeReq>) -> Result<Response<Empty>, Status> { | ||||
|         let req = check_sig_from_req(req)?; | ||||
|         match self.data.find_contract_by_uuid(&req.contract) { | ||||
|             Ok(contract) | ||||
|                 if contract.admin_pubkey == req.admin_pubkey | ||||
|                     && contract.node_pubkey == req.node_pubkey => | ||||
|         match self.data.find_any_contract_by_uuid(&req.contract) { | ||||
|             Ok((Some(vm_contract), _)) | ||||
|                 if vm_contract.admin_pubkey == req.admin_pubkey | ||||
|                     && vm_contract.node_pubkey == req.node_pubkey => | ||||
|             { | ||||
|                 () | ||||
|             } | ||||
|             Ok((_, Some(app_contract))) | ||||
|                 if app_contract.admin_pubkey == req.admin_pubkey | ||||
|                     && app_contract.node_pubkey == req.node_pubkey => | ||||
|             { | ||||
|                 () | ||||
|             } | ||||
|             _ => return Err(Status::unauthenticated("No contract found by this ID.")), | ||||
|         }; | ||||
|         self.data | ||||
|             .report_node(req.admin_pubkey, &req.node_pubkey, req.reason); | ||||
|             .report_any_node(req.admin_pubkey, &req.node_pubkey, req.reason); | ||||
|         Ok(Response::new(Empty {})) | ||||
|     } | ||||
| 
 | ||||
|  | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user