Python Forum
Create new folders and copy files
Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Create new folders and copy files
#1
My task: I have a folder containing many folders named after projects. These project folders have various amounts/levels of subfolders. I want to create new folders with the same name as the project folders in another folder. Then I want to copy files with specific names into the correct newly created project folder. After hours and hours of trial and error I just used chat gpt and got what I belive is pretty close but with one problem that I cant solve. The code creates new folders for all subfolder and not just the project folder. I just want 1 level, new project folders and then all files containing the search words.
(I never coded in Python before and im pretty shit at coding overall so I hope I explained my problem sufficiently)

my(chat gpts) code:
import os
import shutil

# Define the search keywords
search_words = ['Genomförandebeskrivning', 'administrativa föreskrifter', 'AF', 'GB', 'mervärdersbeskrivning']

# Define the input and output directories
input_dir = r'C:\Users\erict\OneDrive\Skrivbord\Anbud'
output_dir = r'C:\Users\erict\OneDrive\Skrivbord\Kopior'

# Walk through the directories and files in the input directory
for dirpath, dirnames, filenames in os.walk(input_dir):
    # Get the corresponding subdirectory path in the output directory
    rel_dirpath = os.path.relpath(dirpath, input_dir)
    output_subdir = os.path.join(output_dir, rel_dirpath)
    os.makedirs(output_subdir, exist_ok=True)

    # Loop through the files in the current directory
    for filename in filenames:
        # Check if the file contains any of the search keywords
        if any(word in filename for word in search_words):
            # Copy the file to the output directory
            input_filepath = os.path.join(dirpath, filename)
            output_filepath = os.path.join(output_subdir, filename)
            shutil.copy2(input_filepath, output_filepath)
Gribouillis write Mar-22-2023, 06:24 AM:
Please post all code, output and errors (it it's entirety) between their respective tags. Refer to BBCode help topic on how to post. Use the "Preview Post" button to make sure the code is presented as you expect before hitting the "Post Reply/Thread" button.
Reply
#2
(Mar-21-2023, 10:29 PM)cocobolli Wrote: I just want 1 level, new project folders and then all files containing the search words.
I can give you a function to traverse all the files of a single directory, recursively or not recursively. This should give you a simple starting point.
import os

def iter_files(directory, recursive=False):
    walk = os.walk(directory)
    if recursive:
        for root, dirs, files in walk:
            for f in files:
                yield os.path.join(root, f)
    else:
        yield from next(walk)[2]


if __name__ == '__main__':
    for f in iter_files('my-directory', recursive=True):
        print(f)
Reply
#3
Instead of walk, you could use glob with pathlib.


import shutil
from pathlib import Path

# if those files do have an extension,
# then you can use path.stem, to get only the name without extension of a Path object
search_words = [
    "Genomförandebeskrivning",
    "administrativa föreskrifter",
    "AF",
    "GB",
    "mervärdersbeskrivning",
]

# more dynamic
# Home is known to the os, then OneDrive/Skrivbord added to path
# then input_dir and output_dir is constructed with the true-division operator
# you can use forward slashes for Windows

base_path = Path.home().joinpath("OneDrive/Skrivbord")
input_dir = base_path / "Anbud"
output_dir = base_path / "Kopior"

for source_element in input_dir.rglob("*"):
    if source_element.is_file() and source_element.stem in search_words:
        target_element = output_dir / source_element.relative_to(input_dir)
        print(source_element, "->", target_element)

        # you culd skip already existing files in the target
        if target_element.exists():
            print(target_element, "exists already")
            print("Skipping ...")
            # you could also check, if the file has the same metadata and size
            # which is not a guarantee that there is no difference in source/target
            # because the metadata and size can be the same, but content can be different
            continue

        # creating the target-directory with all it's parents
        # and ignoring a existing path
        target_element.parent.mkdir(exist_ok=True, parents=True)

        # do not try to blindly copy files, before you have
        # checked if the output is right
        shutil.copy2(source_element, target_element)
EDIT: I've forgotten to add the step where the target-directory is created before the file is copied to the target.
Almost dead, but too lazy to die: https://sourceserver.info
All humans together. We don't need politicians!
Reply
#4
(Mar-22-2023, 10:06 AM)DeaD_EyE Wrote: you could use glob with pathlib.
The drawback of this is that you need to use .is_file() for every path found, so a stat system call for each path. One may expect that os.walk is more efficiently implemented (although I don't have a proof of this).
Reply


Possibly Related Threads…
Thread Author Replies Views Last Post
  Copy Paste excel files based on the first letters of the file name Viento 2 348 Feb-07-2024, 12:24 PM
Last Post: Viento
  Copy only hidden files and folders with rsync Cannondale 2 954 Mar-04-2023, 02:48 PM
Last Post: Cannondale
  Python code to read second line from CSV files and create a master CSV file sh1704 1 2,353 Feb-13-2022, 07:13 PM
Last Post: menator01
  automatic create folders Mr_Kool 4 1,718 Dec-21-2021, 04:38 PM
Last Post: BashBedlam
  Compare filename with folder name and copy matching files into a particular folder shantanu97 2 4,390 Dec-18-2021, 09:32 PM
Last Post: Larz60+
  Moving files to Folders giddyhead 13 9,005 Mar-07-2021, 02:50 AM
Last Post: giddyhead
  code to read files in folders and transfer the file name, type, date created to excel Divya577 0 1,835 Dec-06-2020, 04:14 PM
Last Post: Divya577
  Copy files from subfolders into same name of subfolders at other directory rathoreanil 1 2,305 Oct-12-2020, 01:30 AM
Last Post: Larz60+
  need to define date range of files to copy over OTH 4 3,060 Aug-07-2020, 12:29 PM
Last Post: buran
  Calling Variables from Other Files in Different Folders illmattic 14 5,390 Aug-01-2020, 07:02 PM
Last Post: deanhystad

Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020