Orion9

|
Posted: Sun Sep 06, 2026 17:38 Post subject: |
|
|
| Destiny wrote: | | Вот тоже наткнулся на явную ошибку формирования GUI самописного диалога. |
Так он же явно пишет, что файл существует, поэтому ссылка не может быть создана. Можно добавить на конец что-нибудь типа _1 и посмотреть, что получится и где.
| Destiny wrote: | | И еще другая ошибка. Берете и удаляете в поле "Создать ссылки для..." имя сопсно будущей ссылки. Оставьте там лишь родительскую папку\. |
Так ведь для ссылки нужно имя указать, без этого не будет работать. Например .\ не работает, а .\test или ..\test работает.
| Destiny wrote: | | вы же вроде писали как-то, что у вас получилось от ИИ что-то полезное заполучить? |
Получалось. И не раз )
| Destiny wrote: | | А можете просто вот проверить идею создания схожей программы в рамках питоновского скрипта, к примеру? |
Ну, на счет питоновского скрипта не знаю (нет возможности проверить), а для Autohotkey 2 пожалуйста
 Hidden text | Code: | #Requires AutoHotkey v2.0
#SingleInstance Force
; Проверяем права администратора (они нужны ТОЛЬКО для символических ссылок)
if !A_IsAdmin {
MsgBox("Внимание: Создание СИМВОЛИЧЕСКИХ ссылок требует прав администратора.`nСкрипт будет перезапущен с повышенными правами.", "Инфо", "IconInformation")
Run('*RunAs "' A_ScriptFullPath '"')
ExitApp
}
; Создаем GUI
MyGui := Gui("+AlwaysOnTop", "NTFS Ссылки через DllCall")
MyGui.SetFont("s10", "Segoe UI")
MyGui.AddText("w300", "Выберите тип ссылки:")
RadioHard := MyGui.AddRadio("vLinkType Checked", "Жесткая ссылка (Файл -> Файл)")
RadioSymFile := MyGui.AddRadio("", "Символическая ссылка (Файл -> Файл)")
RadioSymDir := MyGui.AddRadio("", "Символическая ссылка (Папка -> Папка)")
RadioJunction := MyGui.AddRadio("", "Точка соединения / Junction (Папка -> Папка)")
MyGui.AddText("w300 xs y+15", "Путь к оригиналу (Target):")
EditTarget := MyGui.AddEdit("w350 vTarget")
BtnSelectTarget := MyGui.AddButton("x+5 w50", "...")
MyGui.AddText("w300 xs y+15", "Путь для новой ссылки (Link):")
EditLink := MyGui.AddEdit("w350 vLink")
BtnSelectLink := MyGui.AddButton("x+5 w50", "...")
BtnCreate := MyGui.AddButton("xs y+20 w405 Default", "Создать ссылку через API")
; Привязка событий
BtnSelectTarget.OnEvent("Click", SelectTarget)
BtnSelectLink.OnEvent("Click", SaveLink)
BtnCreate.OnEvent("Click", ActionCreateLink)
MyGui.Show()
; --- ФУНКЦИИ ВЫБОРА ПУТЕЙ ---
SelectTarget(*) {
GuiValues := MyGui.Submit(false)
if (GuiValues.LinkType >= 3)
Selected := DirSelect(, 3, "Выберите исходную папку")
else
Selected := FileSelect(3,, "Выберите исходный файл")
if Selected
EditTarget.Value := Selected
}
SaveLink(*) {
GuiValues := MyGui.Submit(false)
if (GuiValues.LinkType >= 3)
Selected := DirSelect(, 3, "Выберите, где создать папку-ссылку")
else
Selected := FileSelect("S16",, "Сохранить ссылку как")
if Selected
EditLink.Value := Selected
}
; --- ОСНОВНАЯ ЛОГИКА DLLCALL ---
ActionCreateLink(*) {
GuiValues := MyGui.Submit(false)
if (GuiValues.Target == "" || GuiValues.Link == "") {
MsgBox("Заполните оба поля!", "Ошибка", "IconExclamation")
return
}
Result := 0
switch GuiValues.LinkType {
case 1: ; Жесткая ссылка (Hard Link) на файл
; CreateHardLinkW(lpFileName, lpExistingFileName, lpSecurityAttributes)
Result := DllCall("CreateHardLinkW", "Str", GuiValues.Link, "Str", GuiValues.Target, "Ptr", 0, "Int")
case 2: ; Символическая ссылка на файл
; CreateSymbolicLinkW(lpSymlinkFileName, lpTargetFileName, dwFlags)
; Флаг 0x0 = Файл, Флаг 0x2 = Разрешить несвежие пути (SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE если включен DevMode)
Result := DllCall("CreateSymbolicLinkW", "Str", GuiValues.Link, "Str", GuiValues.Target, "UInt", 0x0, "UChar")
case 3: ; Символическая ссылка на папку
; Флаг 0x1 = Каталог
Result := DllCall("CreateSymbolicLinkW", "Str", GuiValues.Link, "Str", GuiValues.Target, "UInt", 0x1, "UChar")
case 4: ; Точка соединения (Junction)
; Флаг 0x1 (каталог) + 0x2 (создание виртуального имени/свойства связи) = 0x3
Result := DllCall("CreateSymbolicLinkW", "Str", GuiValues.Link, "Str", GuiValues.Target, "UInt", 0x3, "UChar")
}
if (Result != 0) {
MsgBox("Ссылка успешно создана через Win32 API!", "Успех", "IconInformation")
EditTarget.Value := ""
EditLink.Value := ""
} else {
; Получаем код ошибки Windows, если API вернул 0 (неудача)
ErrorCode := A_LastError
MsgBox("Ошибка API! Не удалось создать ссылку.`nКод ошибки Windows (System Error Code): " ErrorCode, "Ошибка", "IconStop")
}
} |
Я проверил. Работает. Только имена ссылкам нужно давать в поле для новой ссылки.
| Destiny wrote: | | Я б потестил)))) |
А что мешает? Человек болвану друг, это знают все вокруг Болван - друг человека
 Hidden text | Code: | import sys
import ctypes
from tkinter import Tk, Label, Button, Radiobutton, Entry, StringVar, IntVar, messagebox, filedialog
# Проверка прав администратора (символические ссылки требуют повышенных прав)
def is_admin():
try:
return ctypes.windll.shell32.IsUserAnAdmin()
except:
return False
if not is_admin():
# Перезапускаем скрипт с правами администратора
ctypes.windll.shell32.ShellExecuteW(None, "runas", sys.executable, " ".join(sys.argv), None, 1)
sys.exit()
# Инициализация главного окна GUI
root = Tk()
root.title("NTFS Ссылки через Win32 API")
root.geometry("450x380")
root.resizable(False, False)
# Переменные для хранения путей и выбора типа ссылки
link_type = IntVar(value=1)
target_path = StringVar()
link_path = StringVar()
# --- ФУНКЦИИ ВЫБОРА ПУТЕЙ ---
def select_target():
if link_type.get() >= 3:
selected = filedialog.askdirectory(title="Выберите исходную папку")
else:
selected = filedialog.askopenfilename(title="Выберите исходный файл")
if selected:
target_path.set(selected.replace("/", "\\"))
def select_link():
if link_type.get() >= 3:
selected = filedialog.askdirectory(title="Выберите, где создать папку-ссылку")
else:
selected = filedialog.asksaveasfilename(title="Сохранить ссылку как")
if selected:
link_path.set(selected.replace("/", "\\"))
# --- ОСНОВНАЯ ЛОГИКА WIN32 API ---
def create_link():
target = target_path.get()
link = link_path.get()
if not target or not link:
messagebox.showwarning("Ошибка", "Заполните оба поля!")
return
result = 0
t_type = link_type.get()
# Вызовы Win32 API функций через ctypes
if t_type == 1:
# CreateHardLinkW(lpFileName, lpExistingFileName, lpSecurityAttributes)
result = ctypes.windll.kernel32.CreateHardLinkW(link, target, None)
elif t_type == 2:
# CreateSymbolicLinkW(lpSymlinkFileName, lpTargetFileName, dwFlags) | 0x0 = Файл
result = ctypes.windll.kernel32.CreateSymbolicLinkW(link, target, 0x0)
elif t_type == 3:
# 0x1 = Символическая ссылка на каталог
result = ctypes.windll.kernel32.CreateSymbolicLinkW(link, target, 0x1)
elif t_type == 4:
# 0x3 = Точка соединения / Junction (Каталог + Виртуальное имя)
result = ctypes.windll.kernel32.CreateSymbolicLinkW(link, target, 0x3)
if result != 0:
messagebox.showinfo("Успех", "Ссылка успешно создана через Win32 API!")
target_path.set("")
link_path.set("")
else:
# Получаем код ошибки Windows
error_code = ctypes.windll.kernel32.GetLastError()
messagebox.showerror("Ошибка API", f"Не удалось создать ссылку.\nКод ошибки Windows (System Error Code): {error_code}")
# --- ИНТЕРФЕЙС (WIDGETS) ---
Label(root, text="Выберите тип ссылки:", font=("Segoe UI", 10, "bold")).pack(anchor="w", px=15, py=5)
Radiobutton(root, text="Жесткая ссылка (Файл -> Файл)", variable=link_type, value=1).pack(anchor="w", px=20)
Radiobutton(root, text="Символическая ссылка (Файл -> Файл)", variable=link_type, value=2).pack(anchor="w", px=20)
Radiobutton(root, text="Символическая ссылка (Папка -> Папка)", variable=link_type, value=3).pack(anchor="w", px=20)
Radiobutton(root, text="Точка соединения / Junction (Папка -> Папка)", variable=link_type, value=4).pack(anchor="w", px=20)
# Поле Target
Label(root, text="Путь к оригиналу (Target):", font=("Segoe UI", 10)).pack(anchor="w", px=15, py=(15, 0))
target_frame = Entry(root, textvariable=target_path, width=45)
target_frame.pack(side="top", anchor="w", px=15, ipy=3)
Button(root, text="...", command=select_target, width=5).place(x=390, y=183)
# Поле Link
Label(root, text="Путь для новой ссылки (Link):", font=("Segoe UI", 10)).pack(anchor="w", px=15, py=(15, 0))
link_frame = Entry(root, textvariable=link_path, width=45)
link_frame.pack(side="top", anchor="w", px=15, ipy=3)
Button(root, text="...", command=select_link, width=5).place(x=390, y=253)
# Кнопка создания
Button(root, text="Создать ссылку через API", command=create_link, font=("Segoe UI", 10, "bold"), bg="#e1e1e1", width=47).pack(anchor="w", px=15, py=25)
root.mainloop() |
|
|