Skip to content

Commit 1a3704f

Browse files
author
Kaleb Luedtke
committed
Write to file without changing attributes
1 parent af5e1f5 commit 1a3704f

2 files changed

Lines changed: 13 additions & 19 deletions

File tree

doc/ReleaseNotes.md

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,4 @@ The PowerShell module now automatically uses `GH_TOKEN` or `GITHUB_TOKEN` enviro
3838

3939
## Bug Fixes
4040

41-
<!-- Nothing yet! -->
42-
43-
## Bug Fixes
4441
* `winget export` now works when the destination path is a hidden file

src/AppInstallerCLICore/Workflows/ImportExportFlow.cpp

Lines changed: 13 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -158,24 +158,21 @@ namespace AppInstaller::CLI::Workflow
158158

159159
std::filesystem::path outputFilePath{ context.Args.GetArg(Execution::Args::Type::OutputFile) };
160160

161-
// Check if the file exists and is hidden
162-
DWORD attrs = std::filesystem::exists(outputFilePath) ? GetFileAttributesW(outputFilePath.c_str()) : INVALID_FILE_ATTRIBUTES;
161+
// GetFileAttributesW returns INVALID_FILE_ATTRIBUTES for non-existent files, so no separate exists() check is needed.
162+
DWORD attrs = GetFileAttributesW(outputFilePath.c_str());
163163
bool isHidden = (attrs != INVALID_FILE_ATTRIBUTES && (attrs & FILE_ATTRIBUTE_HIDDEN));
164164

165-
if (isHidden)
166-
{
167-
// Remove hidden attribute so we can write to it
168-
SetFileAttributesW(outputFilePath.c_str(), attrs & ~FILE_ATTRIBUTE_HIDDEN);
169-
}
170-
171-
std::ofstream outputFileStream{ outputFilePath };
172-
outputFileStream << packages;
173-
174-
if (isHidden)
175-
{
176-
// Restore hidden attribute
177-
SetFileAttributesW(outputFilePath.c_str(), attrs);
178-
}
165+
// Open the file directly without changing its attributes:
166+
// - For an existing hidden file, use TRUNCATE_EXISTING to clear its content while preserving its attributes.
167+
// - Otherwise, use CREATE_ALWAYS to create a new file or overwrite an existing one.
168+
DWORD creationDisposition = isHidden ? TRUNCATE_EXISTING : CREATE_ALWAYS;
169+
wil::unique_hfile fileHandle{ CreateFileW(outputFilePath.c_str(), GENERIC_WRITE, 0, nullptr, creationDisposition, FILE_ATTRIBUTE_NORMAL, nullptr) };
170+
THROW_LAST_ERROR_IF(!fileHandle);
171+
172+
Json::StreamWriterBuilder writerBuilder;
173+
std::string jsonContent = Json::writeString(writerBuilder, packages);
174+
DWORD bytesWritten = 0;
175+
THROW_LAST_ERROR_IF(!WriteFile(fileHandle.get(), jsonContent.c_str(), static_cast<DWORD>(jsonContent.size()), &bytesWritten, nullptr));
179176
}
180177

181178
void ReadImportFile(Execution::Context& context)

0 commit comments

Comments
 (0)