install_framework_core/command.rs
1// Copyright 2021 Yuri6037
2
3// Permission is hereby granted, free of charge, to any person obtaining a copy
4// of this software and associated documentation files (the "Software"),
5// to deal in the Software without restriction, including without limitation
6// the rights to use, copy, modify, merge, publish, distribute, sublicense,
7// and/or sell copies of the Software, and to permit persons to whom the
8// Software is furnished to do so, subject to the following conditions:
9
10// The above copyright notice and this permission notice shall be included in
11// all copies or substantial portions of the Software.
12
13// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
18// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
19// IN THE SOFTWARE.
20
21use std::collections::HashMap;
22use std::collections::VecDeque;
23
24pub trait Interpreter<TCommand>
25{
26 type ErrorType;
27
28 /// Execute a command
29 ///
30 /// # Arguments
31 ///
32 /// * `resid` - Resource id of the command to be processed
33 /// * `cmd` - The command to execute
34 fn execute(&mut self, resid: usize, cmd: TCommand) -> Result<(), Self::ErrorType>;
35
36 /// Called to let a chance to handle execution progress
37 ///
38 /// # Arguments
39 ///
40 /// * `curcmd` - Current number of commands executed
41 /// * `maxcmd` - Maximum number of commands to execute
42 fn progress(&mut self, curcmd: usize, maxcmd: usize) -> Result<(), Self::ErrorType>;
43}
44
45pub struct CommandQueue<TCommand>
46{
47 queue: VecDeque<(usize, TCommand)>,
48 cur_resource_id: usize
49}
50
51impl <TCommand> CommandQueue<TCommand>
52{
53 pub fn new(cur_resource_id: usize) -> CommandQueue<TCommand>
54 {
55 return CommandQueue
56 {
57 queue: VecDeque::new(),
58 cur_resource_id: cur_resource_id
59 };
60 }
61
62 /// Execute all commands contained in this command queue with the given interpreter
63 ///
64 /// # Arguments
65 ///
66 /// * `interpreter` - The command interpreter
67 pub fn run<TInterpreter: Interpreter<TCommand>>(&mut self, interpreter: &mut TInterpreter) -> Result<(), TInterpreter::ErrorType>
68 {
69 let mut cur = 0;
70 let max = self.queue.len();
71 while let Some((resid, cmd)) = self.queue.pop_front()
72 {
73 interpreter.execute(resid, cmd)?;
74 interpreter.progress(cur, max)?;
75 cur += 1;
76 }
77 return Ok(());
78 }
79
80 /// Push a new command into this command queue
81 ///
82 /// # Arguments
83 ///
84 /// * `resid` - Resource id of the command to be processed
85 /// * `cmd` - The command to execute
86 ///
87 /// # Returns
88 ///
89 /// command resource id to reference the output in subsequent commands
90 pub fn push(&mut self, cmd: TCommand) -> usize
91 {
92 self.cur_resource_id += 1;
93 self.queue.push_back((self.cur_resource_id, cmd));
94 return self.cur_resource_id;
95 }
96
97 /// Gets the last resource index
98 pub fn get_last_resource_id(&self) -> usize
99 {
100 return self.cur_resource_id;
101 }
102}
103
104pub enum InitCommand
105{
106 /// Instructs to download a file into cache
107 ///
108 /// #### Arguments
109 /// * filename,
110 /// * url,
111 /// * headers
112 DownloadFile(String, String, HashMap<String, String>),
113
114 /// Instructs to unpack an archive file from cache
115 ///
116 /// #### Arguments
117 /// * path in cache (use %res:<id>% to mension a file contained in a subfolder in the cache)
118 UnpackCached(String),
119
120 /// Instructs to extract a file contained in this installer's resources to the cache
121 ///
122 /// #### Arguments
123 /// * resource name/path
124 ExtractResource(&'static str),
125
126 /// Instructs to ask the user for input
127 ///
128 /// #### Arguments
129 /// * property name
130 /// * input message
131 UserInput(String, String)
132}
133
134pub enum InstallCommand
135{
136 /// Instructs to download a file into cache
137 ///
138 /// #### Arguments
139 /// * filename,
140 /// * url,
141 /// * headers
142 DownloadFile(String, String, HashMap<String, String>),
143
144 /// Instructs to unpack an archive file from cache
145 ///
146 /// #### Arguments
147 /// * path in cache (use %res:<id>% to mension a file contained in a subfolder in the cache)
148 UnpackCached(String),
149
150 /// Instructs to extract a file contained in this installer's resources to the cache
151 ///
152 /// #### Arguments
153 /// * resource name/path
154 ExtractResource(&'static str),
155
156 /// Instructs to ask the user for input
157 ///
158 /// #### Arguments
159 /// * property name
160 /// * input message
161 UserInput(String, String),
162
163 /// Instructs to install a file contained in this installer's resources
164 ///
165 /// #### Arguments
166 /// * resource name/path,
167 /// * target folder resource id (0 = main content directory)
168 InstallResource(&'static str, usize),
169
170 /// Instructs to create a folder
171 ///
172 /// #### Arguments
173 /// * folder name
174 CreateFolder(String),
175
176 /// Instructs to add a binary file to the PATH
177 ///
178 /// #### Arguments
179 /// * path to file relative to content directory
180 AddToPath(String),
181
182 /// Instructs to install a file or folder from cache
183 ///
184 /// #### Arguments
185 /// * path in cache (use %res:<id>% to mension a file contained in a subfolder in the cache),
186 /// * target folder resource id (0 = main content directory)
187 InstallCached(String, usize),
188
189 /// Instructs to create a shortcut to run a GUI application
190 ///
191 /// #### Arguments
192 /// * path to file relative to content directory
193 AddShortcut(String)
194}