GitRoot

Craft your forge // Build your project // Grow your community freely
  1// SPDX-FileCopyrightText: 2025 Romain Maneschi <romain@gitroot.dev>
  2//
  3// SPDX-License-Identifier: MIT
  4
  5use crate::{
  6    fs::FsBase,
  7    model::{
  8        Call, CallRes, Commit, Exec, ExecStatus, ForgeConf, HttpRequest, HttpResponse,
  9        IteratorItem, ReportToGitroot,
 10    },
 11    ptr::{ptr_to_string, string_to_ptr},
 12};
 13
 14#[link(wasm_import_module = "gitroot")]
 15unsafe extern "C" {
 16    #[link_name = "forgeConf"]
 17    pub unsafe fn _forge_conf() -> u64;
 18    #[link_name = "modifyContent"]
 19    pub unsafe fn _modify_content(
 20        filepathPtr: u32,
 21        filepathSize: u32,
 22        contentPtr: u32,
 23        contentSize: u32,
 24    );
 25    #[link_name = "modifyWebContent"]
 26    pub unsafe fn _modify_web_content(
 27        filepathPtr: u32,
 28        filepathSize: u32,
 29        contentPtr: u32,
 30        contentSize: u32,
 31    );
 32    #[link_name = "replaceWebContent"]
 33    pub unsafe fn _replace_web_content(
 34        filepathPtr: u32,
 35        filepathSize: u32,
 36        oldContentPtr: u32,
 37        oldContentSize: u32,
 38        contentPtr: u32,
 39        contentSize: u32,
 40    );
 41    #[link_name = "modifyCacheContent"]
 42    pub unsafe fn _modify_cache_content(
 43        filepathPtr: u32,
 44        filepathSize: u32,
 45        contentPtr: u32,
 46        contentSize: u32,
 47    );
 48
 49    #[link_name = "copyFile"]
 50    pub unsafe fn _copy_file(
 51        from_fs_ptr: u32,
 52        from_fs_size: u32,
 53        from_path_ptr: u32,
 54        from_path_size: u32,
 55        to_fs_ptr: u32,
 56        to_fs_size: u32,
 57        to_path_ptr: u32,
 58        to_path_size: u32,
 59    ) -> u64;
 60
 61    #[link_name = "deleteFile"]
 62    pub unsafe fn _delete_file(
 63        from_fs_ptr: u32,
 64        from_fs_size: u32,
 65        from_path_ptr: u32,
 66        from_path_size: u32,
 67    ) -> u64;
 68
 69    #[link_name = "moveFile"]
 70    pub unsafe fn _move_file(
 71        from_fs_ptr: u32,
 72        from_fs_size: u32,
 73        from_path_ptr: u32,
 74        from_path_size: u32,
 75        to_fs_ptr: u32,
 76        to_fs_size: u32,
 77        to_path_ptr: u32,
 78        to_path_size: u32,
 79    ) -> u64;
 80
 81    #[link_name = "replaceContent"]
 82    pub unsafe fn _replace_content(
 83        from_fs_ptr: u32,
 84        from_fs_size: u32,
 85        filepath_ptr: u32,
 86        filepath_size: u32,
 87        old_content_ptr: u32,
 88        old_content_size: u32,
 89        content_ptr: u32,
 90        content_size: u32,
 91    ) -> u64;
 92
 93    #[link_name = "writeContent"]
 94    pub unsafe fn _write_content(
 95        from_fs_ptr: u32,
 96        from_fs_size: u32,
 97        filepath_ptr: u32,
 98        filepath_size: u32,
 99        content_ptr: u32,
100        content_size: u32,
101    ) -> u64;
102    #[link_name = "commitAll"]
103    pub unsafe fn _commit_all(ptr: u32, size: u32);
104    #[link_name = "diffWithParent"]
105    pub unsafe fn _diff_with_parent(
106        hash_ptr: u32,
107        hash_size: u32,
108        oldfile_ptr: u32,
109        oldfile_size: u32,
110        newfile_ptr: u32,
111        newfile_size: u32,
112    ) -> u64;
113    #[link_name = "log"]
114    pub unsafe fn _log(ptr: u32, size: u32);
115    #[link_name = "logError"]
116    pub unsafe fn _log_error(messagePtr: u32, messageSize: u32, errPtr: u32, errSize: u32);
117    #[link_name = "merge"]
118    pub unsafe fn _merge(from_ptr: u32, from_size: u32, to_ptr: u32, to_size: u32);
119    #[link_name = "commits"]
120    pub unsafe fn _commits(from_ptr: u32, from_size: u32, to_ptr: u32, to_size: u32) -> u64;
121    #[link_name = "exec"]
122    pub unsafe fn _exec(cmd_ptr: u32, cmd_size: u32) -> u64;
123    #[link_name = "report"]
124    pub unsafe fn _report(report_ptr: u32, report_size: u32);
125    #[link_name = "canCall"]
126    pub unsafe fn _can_call(report_ptr: u32, report_size: u32) -> u32;
127    #[link_name = "call"]
128    pub unsafe fn _call(report_ptr: u32, report_size: u32) -> u64;
129    #[link_name = "httpClient"]
130    pub unsafe fn _http_client(ptr: u32, size: u32) -> u64;
131    #[link_name = "iteratorNext"]
132    pub unsafe fn _iterator_next(ptr: u32, size: u32) -> u64;
133}
134
135pub(crate) fn forge_conf() -> Result<ForgeConf, String> {
136    unsafe {
137        let ptr_size: u64 = _forge_conf();
138        if ptr_size == 0 {
139            return Err(String::from("can't get  forge_conf"));
140        }
141        let ptr: u32 = (ptr_size >> 32) as u32;
142        let size: u32 = ptr_size as u32;
143        Ok(serde_json::from_str(ptr_to_string(ptr, size).as_str())
144            .expect("JSON was not well-formatted"))
145    }
146}
147
148pub(crate) fn copy_file(
149    from_fs: FsBase,
150    from_path: String,
151    to_fs: FsBase,
152    to_path: String,
153) -> Result<(), String> {
154    let (from_fs_ptr, from_fs_size) = string_to_ptr(from_fs.as_str());
155    let (from_path_ptr, from_path_size) = string_to_ptr(&from_path);
156    let (to_fs_ptr, to_fs_size) = string_to_ptr(to_fs.as_str());
157    let (to_path_ptr, to_path_size) = string_to_ptr(&to_path);
158    unsafe {
159        let ptr_size: u64 = _copy_file(
160            from_fs_ptr,
161            from_fs_size,
162            from_path_ptr,
163            from_path_size,
164            to_fs_ptr,
165            to_fs_size,
166            to_path_ptr,
167            to_path_size,
168        );
169        if ptr_size == 0 {
170            return Ok(());
171        }
172        let ptr: u32 = (ptr_size >> 32) as u32;
173        let size: u32 = ptr_size as u32;
174        Err(ptr_to_string(ptr, size))
175    }
176}
177
178pub(crate) fn delete_file(from_fs: FsBase, from_path: String) -> Result<(), String> {
179    let (from_fs_ptr, from_fs_size) = string_to_ptr(from_fs.as_str());
180    let (from_path_ptr, from_path_size) = string_to_ptr(&from_path);
181    unsafe {
182        let ptr_size: u64 = _delete_file(from_fs_ptr, from_fs_size, from_path_ptr, from_path_size);
183        if ptr_size == 0 {
184            return Ok(());
185        }
186        let ptr: u32 = (ptr_size >> 32) as u32;
187        let size: u32 = ptr_size as u32;
188        Err(ptr_to_string(ptr, size))
189    }
190}
191
192pub(crate) fn move_file(
193    from_fs: FsBase,
194    from_path: String,
195    to_fs: FsBase,
196    to_path: String,
197) -> Result<(), String> {
198    let (from_fs_ptr, from_fs_size) = string_to_ptr(from_fs.as_str());
199    let (from_path_ptr, from_path_size) = string_to_ptr(&from_path);
200    let (to_fs_ptr, to_fs_size) = string_to_ptr(to_fs.as_str());
201    let (to_path_ptr, to_path_size) = string_to_ptr(&to_path);
202    unsafe {
203        let ptr_size: u64 = _move_file(
204            from_fs_ptr,
205            from_fs_size,
206            from_path_ptr,
207            from_path_size,
208            to_fs_ptr,
209            to_fs_size,
210            to_path_ptr,
211            to_path_size,
212        );
213        if ptr_size == 0 {
214            return Ok(());
215        }
216        let ptr: u32 = (ptr_size >> 32) as u32;
217        let size: u32 = ptr_size as u32;
218        Err(ptr_to_string(ptr, size))
219    }
220}
221
222pub(crate) fn replace_content(
223    from_fs: FsBase,
224    filepath: String,
225    old_content: String,
226    content: String,
227) -> Result<(), String> {
228    let (from_fs_ptr, from_fs_size) = string_to_ptr(from_fs.as_str());
229    let (filepath_ptr, filepath_size) = string_to_ptr(&filepath);
230    let (old_content_ptr, old_content_size) = string_to_ptr(&old_content);
231    let (content_ptr, content_size) = string_to_ptr(&content);
232    unsafe {
233        let ptr_size: u64 = _replace_content(
234            from_fs_ptr,
235            from_fs_size,
236            filepath_ptr,
237            filepath_size,
238            old_content_ptr,
239            old_content_size,
240            content_ptr,
241            content_size,
242        );
243        if ptr_size == 0 {
244            return Ok(());
245        }
246        let ptr: u32 = (ptr_size >> 32) as u32;
247        let size: u32 = ptr_size as u32;
248        Err(ptr_to_string(ptr, size))
249    }
250}
251
252pub(crate) fn write_content(
253    from_fs: FsBase,
254    filepath: String,
255    content: String,
256) -> Result<(), String> {
257    let (from_fs_ptr, from_fs_size) = string_to_ptr(from_fs.as_str());
258    let (filepath_ptr, filepath_size) = string_to_ptr(&filepath);
259    let (content_ptr, content_size) = string_to_ptr(&content);
260    unsafe {
261        let ptr_size: u64 = _write_content(
262            from_fs_ptr,
263            from_fs_size,
264            filepath_ptr,
265            filepath_size,
266            content_ptr,
267            content_size,
268        );
269        if ptr_size == 0 {
270            return Ok(());
271        }
272        let ptr: u32 = (ptr_size >> 32) as u32;
273        let size: u32 = ptr_size as u32;
274        Err(ptr_to_string(ptr, size))
275    }
276}
277
278pub(crate) fn commit_all(message: String) {
279    let (msg_ptr, msg_size) = string_to_ptr(&message);
280    unsafe {
281        _commit_all(msg_ptr, msg_size);
282    }
283}
284
285pub(crate) fn diff_with_parent(
286    hash: String,
287    oldfile: String,
288    newfile: String,
289) -> Result<String, String> {
290    let (hash_ptr, hash_size) = string_to_ptr(&hash);
291    let (oldfile_ptr, oldfile_size) = string_to_ptr(&oldfile);
292    let (newfile_ptr, newfile_size) = string_to_ptr(&newfile);
293    unsafe {
294        let ptr_size = _diff_with_parent(
295            hash_ptr,
296            hash_size,
297            oldfile_ptr,
298            oldfile_size,
299            newfile_ptr,
300            newfile_size,
301        );
302        if ptr_size == 0 {
303            return Err(String::from("can't get diff_with_parent"));
304        }
305        let ptr: u32 = (ptr_size >> 32) as u32;
306        let size: u32 = ptr_size as u32;
307        Ok(ptr_to_string(ptr, size))
308    }
309}
310
311pub(crate) fn log(message: &str) {
312    let (msg_ptr, msg_size) = string_to_ptr(message);
313    unsafe {
314        _log(msg_ptr, msg_size);
315    }
316}
317
318pub(crate) fn log_error(message: &str, err: &str) {
319    let (msg_ptr, msg_size) = string_to_ptr(message);
320    let (err_ptr, err_size) = string_to_ptr(err);
321    unsafe {
322        _log_error(msg_ptr, msg_size, err_ptr, err_size);
323    }
324}
325
326pub(crate) fn merge(from: String, to: String) {
327    let (from_ptr, from_size) = string_to_ptr(&from);
328    let (to_ptr, to_size) = string_to_ptr(&to);
329    unsafe {
330        _merge(from_ptr, from_size, to_ptr, to_size);
331    }
332}
333
334pub(crate) fn commits(from: String, to: String) -> Result<Vec<Commit>, String> {
335    let (from_ptr, from_size) = string_to_ptr(&from);
336    let (to_ptr, to_size) = string_to_ptr(&to);
337    unsafe {
338        let ptr_size = _commits(from_ptr, from_size, to_ptr, to_size);
339        if ptr_size == 0 {
340            return Err(String::from("can't get  commits"));
341        }
342        let ptr: u32 = (ptr_size >> 32) as u32;
343        let size: u32 = ptr_size as u32;
344        Ok(serde_json::from_str(ptr_to_string(ptr, size).as_str())
345            .expect("JSON was not well-formatted"))
346    }
347}
348
349pub(crate) fn exec(exec: &Exec) -> Result<ExecStatus, String> {
350    let exec_json = serde_json::to_string(&exec).unwrap();
351    let (cmd_ptr, cmd_size) = string_to_ptr(&exec_json);
352    unsafe {
353        let ptr_size = _exec(cmd_ptr, cmd_size);
354        if ptr_size == 0 {
355            return Err(String::from("can't exec"));
356        }
357        let ptr: u32 = (ptr_size >> 32) as u32;
358        let size: u32 = ptr_size as u32;
359        Ok(serde_json::from_str(ptr_to_string(ptr, size).as_str())
360            .expect("JSON was not well-formatted"))
361    }
362}
363
364pub(crate) fn report_to_gitroot(report: ReportToGitroot) {
365    let report_json = serde_json::to_string(&report).unwrap();
366    let (cmd_ptr, cmd_size) = string_to_ptr(&report_json);
367    unsafe {
368        _report(cmd_ptr, cmd_size);
369    }
370}
371
372pub(crate) fn can_call(call: &Call) -> u32 {
373    let call_json = serde_json::to_string(&call).unwrap();
374    let (ptr, size) = string_to_ptr(&call_json);
375    unsafe { _can_call(ptr, size) }
376}
377
378pub(crate) fn call(call: &Call) -> Result<CallRes, String> {
379    let call_json = serde_json::to_string(&call).unwrap();
380    let (ptr, size) = string_to_ptr(&call_json);
381    unsafe {
382        let ptr_size = _call(ptr, size);
383        if ptr_size == 0 {
384            return Err(String::from("can't call"));
385        }
386        let ptr: u32 = (ptr_size >> 32) as u32;
387        let size: u32 = ptr_size as u32;
388        Ok(serde_json::from_str(ptr_to_string(ptr, size).as_str())
389            .expect("JSON was not well-formatted"))
390    }
391}
392
393pub(crate) fn http_client(request: &HttpRequest) -> Result<HttpResponse, String> {
394    let request_json = serde_json::to_string(&request).unwrap();
395    let (ptr, size) = string_to_ptr(&request_json);
396    unsafe {
397        let ptr_size = _http_client(ptr, size);
398        if ptr_size == 0 {
399            return Err(String::from("can't http"));
400        }
401        let ptr: u32 = (ptr_size >> 32) as u32;
402        let size: u32 = ptr_size as u32;
403        Ok(serde_json::from_str(ptr_to_string(ptr, size).as_str())
404            .expect("JSON was not well-formatted"))
405    }
406}
407
408pub(crate) fn iterator_next(ptr: u32, size: u32) -> Result<IteratorItem, String> {
409    unsafe {
410        let ptr_size = _iterator_next(ptr, size);
411        if ptr_size == 0 {
412            return Err(String::from("can't iterator_next"));
413        }
414        let ptr: u32 = (ptr_size >> 32) as u32;
415        let size: u32 = ptr_size as u32;
416        Ok(serde_json::from_str(ptr_to_string(ptr, size).as_str())
417            .expect("JSON was not well-formatted"))
418    }
419}