CH-J ToolsSSH를 통한 서버 관리
메뉴
공개된 소스

CH-J Tools

특정 애플리케이션 릴리스의 디렉터리와 파일을 살펴보세요.

소스 ZIP 다운로드
CH-J / Server Manager 1704 개 파일
0.1.2-beta 추가됨: · 빌드됨:
lockfile.rs 추가됨: 날짜 기록 없음 3.9 KB · 107 줄
코드 파일 다운로드
1//! Windows daemon protocol, kept platform-independent so the locking and stop files can be tested anywhere.
2#![cfg_attr(unix, allow(dead_code))]
4use std::fs::{self, File, OpenOptions, TryLockError};
5use std::io;
6use std::path::Path;
8const LOCK: &str = "standby-helper.lock";
9const STOP: &str = "standby-helper.stop";
11/// Keep the returned file alive for the daemon's lifetime. Never unlink the lock file: probes and other
12/// instances must always lock the same file, including after an instance exits.
13pub fn acquire(data: &Path) -> io::Result<Option<File>> {
14 fs::create_dir_all(data)?;
15 let file = OpenOptions::new().create(true).truncate(false).read(true).write(true).open(data.join(LOCK))?;
16 match file.try_lock() {
17 Ok(()) => Ok(Some(file)),
18 Err(TryLockError::WouldBlock) => Ok(None),
19 Err(TryLockError::Error(error)) => Err(error),
20 }
23/// A fresh handle distinguishes contention from open/locking errors; any successful probe lock is
24/// released immediately when the local handle is dropped.
25pub fn held_by_other(data: &Path) -> bool {
26 let Ok(file) = OpenOptions::new().read(true).write(true).open(data.join(LOCK)) else { return false };
27 matches!(file.try_lock(), Err(TryLockError::WouldBlock))
30pub fn request_stop(data: &Path) -> io::Result<()> {
31 File::create(data.join(STOP)).map(|_| ())
34pub fn take_stop_request(data: &Path) -> bool {
35 fs::remove_file(data.join(STOP)).is_ok()
38/// Called only after acquiring the instance lock, before starting the workers.
39pub fn clear_stale_stop(data: &Path) -> io::Result<()> {
40 match fs::remove_file(data.join(STOP)) {
41 Err(error) if error.kind() != io::ErrorKind::NotFound => Err(error),
42 _ => Ok(()),
43 }
46#[cfg(test)]
47mod tests {
48 use super::*;
50 #[test]
51 fn second_acquire_fails_until_the_first_handle_is_dropped() {
52 let data = tempfile::tempdir().unwrap();
53 let first = acquire(data.path()).unwrap().unwrap();
54 assert!(held_by_other(data.path()));
55 assert!(acquire(data.path()).unwrap().is_none());
56 drop(first);
57 assert!(!held_by_other(data.path()));
58 assert!(acquire(data.path()).unwrap().is_some());
59 }
61 #[test]
62 fn probe_does_not_keep_a_lock_or_create_missing_data() {
63 let data = tempfile::tempdir().unwrap();
64 let missing = data.path().join("missing");
65 assert!(!held_by_other(&missing));
66 assert!(!missing.exists());
67 drop(acquire(&missing).unwrap().unwrap());
68 assert!(!held_by_other(&missing));
69 assert!(!held_by_other(&missing));
70 assert!(acquire(&missing).unwrap().is_some());
71 }
73 #[test]
74 fn stop_request_is_seen_once_and_removed() {
75 let data = tempfile::tempdir().unwrap();
76 assert!(!take_stop_request(data.path()));
77 request_stop(data.path()).unwrap();
78 assert!(take_stop_request(data.path()));
79 assert!(!data.path().join(STOP).exists());
80 assert!(!take_stop_request(data.path()));
81 }
83 #[test]
84 fn startup_clears_a_stale_stop_request() {
85 let data = tempfile::tempdir().unwrap();
86 request_stop(data.path()).unwrap();
87 let _lock = acquire(data.path()).unwrap().unwrap();
88 clear_stale_stop(data.path()).unwrap();
89 assert!(!data.path().join(STOP).exists());
90 assert!(!take_stop_request(data.path()));
91 clear_stale_stop(data.path()).unwrap();
92 request_stop(data.path()).unwrap();
93 assert!(take_stop_request(data.path()));
94 }
96 #[test]
97 fn filesystem_errors_are_not_reported_as_lock_contention() {
98 let data = tempfile::tempdir().unwrap();
99 fs::create_dir(data.path().join(LOCK)).unwrap();
100 assert!(acquire(data.path()).is_err());
101 assert!(!held_by_other(data.path()));
102 fs::create_dir(data.path().join(STOP)).unwrap();
103 assert!(request_stop(data.path()).is_err());
104 assert!(clear_stale_stop(data.path()).is_err());
105 assert!(!take_stop_request(data.path()));
106 }
SHA-25665ba1ab359e17dba209108c2dc6520f2ed4bf5b8663390d129ebaa5ccc55494c

CH-J Proprietary Software License 1.14 · 소스는 CH-J Proprietary Software License 1.14에 따라 제공됩니다. 소스를 공개한다고 해서 라이선스 조항이 바뀌거나 추가 권리가 부여되지는 않습니다.

압축 파일 SHA-256ac8fe790f4ba60fc098f8c985fc2656cfcc6cdc21fb34b30e308a2b54e62258f
파일