I am having trouble with matching variables to lines in txt, and removing the lines.
I am currently doing a hotel room booking program in which I am having trouble removing a booking from my text file.
This is how my lines in my text file are formatted:
first_name1, phonenumber1 and email 1 are linked to entry boxes
jeff;jeff#gmail.com;123123123;2019-06-09;2019-06-10;Single Room
def edit_details(self,controller):
f = open("Bookings.txt")
lines = f.readlines()
f.close()
x = -1
for i in lines:
x += 1
data = lines[x]
first_name1 = str(controller.editName.get())
phonenumber1 = str(controller.editPhone.get())
email1 = str(controller.editEmail.get())
checkfirst_name, checkemail, checkphone_num, checkclock_in_date, checkclock_out_date, checkroom = map(str, data.split(";"))
if checkfirst_name.upper() == first_name1.upper() and checkemail.upper() == email1.upper() and checkphone_num == phonenumber1:
controller.roomName.set(checkfirst_name)
controller.roomEmail.set(checkemail)
controller.roomPhone.set(checkphone_num)
controller.roomCheckin.set(checkclock_in_date)
controller.roomCheckout.set(checkclock_out_date)
controller.roomSelect.set(checkroom)
print(controller.roomName.get())
print(controller.roomSelect.get())
controller.show_frame("cancelBooking")
break
elif x > len(lines) - int(2):
messagebox.showerror("Error", "Please Enter Valid Details")
break
I have the user to enter their details to give me the variables but I don't know how to match these variables to the line in the text file to remove the booking.
Do I have to format these variables to match the line?
This is what i have tried but it deletes the last line in my file
line_to_match = ';'.join([controller.roomName.get(),controller.roomEmail.get(),controller.roomPhone.get()])
print(line_to_match)
with open("Bookings.txt", "r+") as f:
line = f.readlines()
f.seek(0)
for i in line:
if i.startswith(line_to_match):
f.write(i)
f.truncate()
I have kind of added a pseudocode here. You can join the variables using ; and validate if the line startswith those details, like below.
first_name1, phonenumber1, email1 = 'jeff', 'jeff#gmail.com', '123123123'
line_to_match = ';'.join([first_name1, email1, phonenumber1])
for i in line:
...
if i.startswith(line_to_match):
# Add your removal code here
...
Related
so i'm working on a school proj and i've been trying to get a function to work for over a week, i still haven't been able to, i need to be able to delete a contact which takes up two lines on the code, the code either erases everything, keeps only the two lines, keeps only one line, or doubles every line except the first one which he erases, please help
contact = input("enter the contact you want to delete")
with open("repertoire.txt", "r") as f:
lines = f.readlines()
with open("repertoire.txt", "w") as g:
for line in lines:
if contact in line:
g.write(line)
rang = lines.index(line)
t = lines[rang + 1]
g.write(t)
This should work:
contact = input("enter the contact you want to delete")
with open("repertoire.txt", "r") as f:
lines = f.readlines()
for idx, line in enumerate(lines):
if contact in line:
lines[idx] = ""
with open("repertoire.txt", "w") as f:
for line in lines:
f.write(line)
I'm trying to write the text fields values to a file like this (where inputtxt is a Text widget):
input_file_name = inputtxt1.get('1.0', 'end-1c').replace(" ","")
num_of_compare_points = inputtxt2.get('1.0','end-1c')
VER = inputtxt3.get('1.0','end-1c')
mode = inputtxt4.get(1.0','end-1c')
executionMode = inputtxt5.get('1.0','end-1c')
numOfWorkers = inputtxt6.get ('1.0','end-1c')
sessionFile = inputtxt7.get('1.0','end-1c')
file = open("file_1.setup","w")
file.write (input_file_name + "\n" + num_of_compare_points + "\n" + Option+"\n"+VER+"\n"+mode+"\n"+executionMode+"\n"+numOfWorkers+"\n"+sessionFile)
This method was good but I want to write the variable name +the value to the file so that the user can fill the values from the file not only through GUI and the order in file will be irrelevant since we're storing in the variable itself , Example:
File_1.setup:
input_file_name = (some name the user can change it from here not from GUI)
num_of_compare_points = (some number the user can change it from here not from GUI)
.
.
.
etc
UPDATE: I'm using the file attribute:value in a restore finction which put the value of each attribute on its related text field ; the problem here that I have only the value but not the variable:value and the variables must be in order (I need the order to be irrelevent since I'll use the variable name)
def restore_info():
if os.stat('file_1.setup').st_size == 0:
print("Writing to setup file..")
else:
with open('file_1.setup','r') as f:
lines = list(line for line in (l.strip() for l in f) if line)
x = len(lines)
print (x)
for i in lines:
print (i)
if (x==7):
inputtxt1.insert('end',lines[0])
inputtxt2.insert('end',lines[1])
inputtxt3.insert['end',lines[2])
... etc
UPDATE2 : I've managed to split each line based on ":" but I need a way to tell the program where is variable and where is value
def restore_info():
if os.stat('file_1.setup').st_size == 0:
print("Writing to setup file..")
else:
with open('file_1.setup','r') as f:
lines = list(line for line in (l.strip() for l in f) if line)
x = len(lines)
print (x)
for i in lines:
splitted_i=i.split(":")
print (splitted_i)
UPDATE 3:Advantage of this step
User will be able to apply the value manually, and not only through GUI.
The order will be irrelevant.
Any amount of spaces should be allowed around and in between the variable name and its value.
It will be very easy to search file_1.setup and extract the value for each field.
What you need to do is to collect the data into a dict and dump it as key value pair
sessionFile = 'x'
executionMode = 'y'
data = {'sessionFile': sessionFile, 'executionMode': executionMode}
with open('out.txt', 'w') as f:
for k, v in data.items():
f.write(f'{k}:{v}\n')
out.txt
sessionFile:x
executionMode:y
there is a part of my program where I would like to pass a sorted list of names from a text file to a function which asks the user to enter a name and then indicate whether the name entered is found in the list or not. If the name is found, its position (i.e. index) is also printed.
The file is just 30 names, but when the second function is executed, it will show this after I input which name I would like to search for:
name not found.
name not found.
name found
name not found.
name not found.
...etc for all 30 names.
Here's the code:
def main():
infile = open('names.txt', 'r')
line = infile.readline()
while line !='':
line = line.rstrip('\n')
print(line)
line = infile.readline()
print('\nHere are the names sorted:\n')
infile = open("names.txt", 'r')
names = infile.readlines()
names.sort()
for line in names:
line = line.rstrip('\n')
print(line)
line = infile.readline()
search_file(line) # I don't this this is the correct way to
# pass the sorted list of names?
def search_file(line):
search = open('names.txt', 'r')
user_search = input('\nSearch for a name(Last, First): ')
#item_index = line.index(search)
print()
with open('names.txt', 'r') as f:
for line in f:
if user_search in line:
print('name found')#, item_index)
else:
print('name not found.')
updated code here:
this time it always displays "not found"
def search_file(line):
user_search = input('\nSearch for a name(Last, First): ')
print()
try:
item_index = line.index(user_search)
print(user_search, 'found at index', item_index)
except ValueError:
print('not found.')
Well first you would only want to open the file you are searching one time. You could load all lines in the file into a list with .readlines() this function returns a string in a list for each line. Then you can search for the user string with in each line with
for l in lines:
if (l.find(userstring)>-1):
foundvar=True
I'm making a program that stores data in a text file, I can search for data line by line, and I made a (delete function) that is quoted below, making a variable 'a' adding to it the (non deleted lines), and ask before deletion for results and if not confirmed it would be added also to 'a', then rewrite the (file) with'a' omitting the deleted lines.
THE PROBLEM IS:
all results are deleted not only the confirmed one desbite that:
#deleting line
confirm = input('confirm to delete [y]/[n]>>')
if confirm != 'y':
a += line
so, why did this problem happen and how to fix it?
Next is the whole code of delete function:
searching = input('enter any information about query: ')
searching = searching.lower() # converting words in lower case
f = open(file, 'r')
lines = f.readlines()
f.close()
print('Word | Definition | Remarks')
a = '' # we will store our new edited text here
for line in lines:
line_lower_case = line.lower() # changing line in lower case temporary
# because contact != COntact and will not appear in searcch
if searching in line_lower_case:
print('Query found')
print()
print('>>',line, end = '') # printing words in the same case as been added
# end = '', to prevent printing new line avoiding extra empty line
#deleting line
confirm = input('confirm to delete [y]/[n]>>')
if confirm != 'y':
a += line
#elif confirm =='y':
# pass # it will just do nothing, and will not add line to 'a'
continue # to search for more queries with the same searching entry
print()
a += line #we add each line to the 'a' variable
f = open(file,'w')
f.write(a) #we save our new edited text to the file
f.close()
I changed the indentations of the program and that was the issue as I agreed with #TheLazyScripter and that should work now if I understood your problem correctly, I did a bunch of tests and they did work. I noticed that you didn't define what input file will be and I add that line of code at line 3 which will through an error if the file not defined.
searching = input('enter any information about query: ')
searching = searching.lower() # converting words in lower case
file = "test.txt" #your file
f = open(file, 'r')
lines = f.readlines()
f.close()
print('Word | Definition | Remarks')
a = '' # we will store our new edited text here
for line in lines:
line_lower_case = line.lower() # changing line in lower case temporary
# because contact != COntact and will not appear in searcch
if searching in line_lower_case:
print('Query found')
print()
print('>>',line, end = '') # printing words in the same case as been added
# end = '', to prevent printing new line avoiding extra empty line
#deleting line
confirm = input('confirm to delete [y]/[n]>>')
if confirm != 'y':
a += line
#elif confirm =='y':
# pass # it will just do nothing, and will not add line to 'a'
continue # to search for more queries with the same searching entry
print()
a += line #we add each line to the 'a' variable
f = open(file,'w')
f.write(a) #we save our new edited text to the file
f.close()
I have a file which contains a user:
Sep 15 04:34:31 li146-252 sshd[13326]: Failed password for invalid user ronda from 212.58.111.170 port 42579 ssh2
Trying to use index method for string to edit the user within the file. So far I am able to print the user but now to delete and put in the new user.
newuser = 'PeterB'
with open ('test.txt') as file:
for line in file.readlines():
lines = line.split()
string = ' '.join(lines)
print string.index('user')+1
Do you want to update the file contents? If so, you can update the user name, but you will need to rewrite the file, or write to a second file (for safety):
keyword = 'user'
newuser = 'PeterB'
with open('test.txt') as infile, open('updated.txt', 'w') as outfile:
for line in infile.readlines():
words = line.split()
try:
index = words.index(keyword) + 1
words[index] = newuser
outfile.write('{}\n'.format(' '.join(words)))
except (ValueError, IndexError):
outfile.write(line) # no keyword, or keyword at end of line
Note that this code assumes that each word in the output file is to be separated by a single space.
Also note that this code does not drop lines that do not contain the keyword in them (as do other solutions).
If you want to preserve the original whitespace, regular expressions are very handy, and the resulting code is comparatively simple:
import re
keyword = 'user'
newuser = 'PeterB'
pattern = re.compile(r'({}\s+)(\S+)'.format(keyword))
with open('test.txt') as infile, open('updated.txt', 'w') as outfile:
for line in infile:
outfile.write(pattern.sub(r'\1{}'.format(newuser), line))
If you want to change the names in your log, here is how.
file = open('tmp.txt', 'r')
new_file = []
for line in file.readlines(): # read the lines
line = (line.split(' '))
line[10] = 'vader' # edit the name
new_file.append(' '.join(line)) # store the changes to a variable
file = open('tmp.txt', 'w') # write the new log to file
[file.writelines(line) for line in new_file]