Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
Questions must demonstrate a minimal understanding of the problem being solved. Tell us what you've tried to do, why it didn't work, and how it should work. See also: Stack Overflow question checklist
Closed 9 years ago.
Improve this question
I would like to prompt the user to input number of users to run and email addresses to populate a csv file. I am getting some syntax error. How do I get this working ?
enter code here
import csv
# Define users
valid_input = False
while not valid_input:
users =raw_input('Number of users: ')
try:
users = range(0,int(users)
valid_input = True
except:
print "Invalid input"
pass
First_Name = ["Test"+str(user) for user in range(1, users+1)]
Last_Name = ["User%s" %user for user in users]
email_addresses = []
for user in users:
email= raw_input("Email domain for user %d: " %user)
email_addresses.append(last_names[user] + email)
Password = ["Password1" for user in users]
Group =["Test" for user in users]
Admin = ["Yes" for user in users]
# open a file for writing.
# open a file for writing.
with open('users.csv', 'wb') as csv_out:
writer = csv.writer(csv_out)
writer.writerows(zip(Email_Address, Password, First_Name, Last_Name, Group, Admin))
The line
Email_Address = (raw_input('Email_Address') [Last_Names + "Email_Address " for Last_Names inLast_Name]])
is invalid syntax. It's actually very difficult to tell what you're trying to do with that line, but it is very invalid syntax.
Also you seem to be misunderstanding iteration in python. On your first line you prompt for a single number and then try to iterate through it in multiple other places, which I'm guessing is pretty far from your intention.
users = (raw_input('number of users'))
will set users equal to a single string. I'm guessing that what you'd actually want is something more like this:
valid_input = False
while not valid_input:
users =raw_input('Number of users: ')
try:
users = range(0,int(users))
valid_input = True
except:
print "Invalid input"
pass
I've been reading through the code some more and while it seems to be pretty far from what you've written there, I'm guessing that you want to prompt the user for an email address for each user. If that is indeed the case, this is how you would do it:
email_addresses = []
for user in users:
email = raw_input("Email address for user %d: " %user)
email_addresses.extend([email + last_name for last_name in last_names])
Apparently I was mistaken about your intent, here's a solution for what you're looking for:
email_addresses = []
for user in users:
email= raw_input("Email domain for user %d: " %user)
email_addresses.append(last_names[user] + email)
Also, a couple style notes:
Try to keep all of your variable names as descriptive as possible. For instance, the last_name list you've got doesn't actually have last names, but holds user ids, so user_ids would be a better name
If you are going to adopt a pluralization nomenclature then make sure to pluralize lists and then make sure that the items can be referenced as the singular version instead of the other way around. For example:
last_name = [#some list]
[#something for last_names in last_name]
is just confusing. It should be:
last_names = [#some_list]
[#something for last_name in last_names]
Choose either snake case (like_this) or title case (likeThis) and stick with it. Nothing is more annoying than having to scroll through a lost codebase and figure out which case a particular variable is using.
I'm not into Python at all, but it seems to be 1 square bracket too much at the end of this line :
Email_Address = (raw_input('Email_Address') [Last_Names + "Email_Address " for Last_Names inLast_Name]])
After this line:
users = (raw_input('number of users'))
users is a string. Let's say you enter 100.
Now, you iterate over users:
First_Name = ["Test"+str(user) for user in users]
Strings are iterable, so user takes on the individual characters of the string '100'. That is, user will first be '1', then '0', then '0' again; you get Test1 then Test0 then Test0 rather than the 100 items I expect you expect.
You probably want to convert the input to an integer:
users = int(raw_input('number of users'))
And then iterate over a range (I'm assuming you want 1 through n rather than 0 through n-1:
First_Names = ["Test"+str(user) for user in range(1, users+1)]
I've also taken the liberty of changing the name of your variable to First_Names as what you have is a list of the first names, not a single first name.
Unfortunately, I don't really have the time to go into the rest of the problems with your code, of which there are many (including the question about input that you're actually asking), but that ought to get you started fixing it up.
Related
I am fairly new to python programming and after finishing a bunch of beginners trainings id like to get some hands on experience.
My idea was to develop a account/password distribution tool.
What it should do is:
Import csv with accounts, users, permissions (Username1,Account1-PasswordPart1, Account2-PasswordPart2)
iterate through accounts.csv (generate and attach pw to account object)
iterate through users.csv (generate encrypted zip with *.txt for each users that contains accounts and half the password based on the permissions.csv)
1. Import
The import was fairly easy to implement.
2. Generate Password
This is the function I use to generate the passwords:
def pw_generator(length):
#define data
lower = string.ascii_lowercase
upper = string.ascii_uppercase
num = string.digits
symbols = string.punctuation
#string.ascii_letters
#combine the data
all = lower + upper + num + symbols
#use random
randompw = random.sample(all,length)
#create the password
password = "".join(randompw)
#print the password
return password
3. Use accounts.csv and make an object out of it
This is were im currently stuck. I tried this .. (and many other approaches)
class account:
def __init__(self,accountname,password):
self.accountname = accountname
self.password = password
acc_list = []
with open('accounts.csv', newline='') as csv_file:
reader = csv.reader(csv_file)
next(reader, None) # Skip the header.
for accountname, password in reader:
acc_list.append(account(account, password))
account.password=pw_generator(16)
print(accountname, account.password)
This gives me a list of the accountnames and passwords but I dont see how i can use them afterwards as an array..
Any ideas?
Thanks!
First, you have dug yourself a hole by giving a class a lowercase name.
This thing:
acc_list.append(account(account, password))
If you rename the class account into class Account and refactor the code, you'll see that it doesn't make any sense:
acc_list.append(Account(Account, password))
You create an instance of a class Account by giving it the class Account as an accountname. It doesn't seem like the thing you want to do.
And then you also change an undeclared class attribute (not the instance attribute, but the class attribute!):
Account.password=pw_generator(16)
Which also looks extremely suspicious, to put it mildly.
Second, it's not obvious what the field password should be in the end. Is it the value you read from .csv? Or some autogenerated pw?
You probably wanted to do something like this:
for accountname, password in reader:
acc_instance = Account(accountname, password) # Create an instance
acc_list.append(acc_instance) # add the instance to the list
print(acc_instance.accountname, acc_instance.password) # print the instance
# Then you can do whatever you like with the list.
# For example you could redefine all passwords in all accounts and print new credentials:
for acc in acc_list:
acc.password = pw_generator(16)
print(acc.accountname, acc.password)
# Or save this list in whatever form you like.
I manage a booking system where people enter their emails to book appointments. Unfortunately, many of the email addresses have typos, especially in the top-level domain. I'd like to implement a function to identify when the domain should be .com, which should be all cases where it starts with ".c".
I wrote the function and tested the individual lines, which seem to work. But when I run the function on a set of emails, it only returns the email with no ".c", meaning it only returns 'my_name_is#orange.org'. The ideal output would be:
['me.you#perp.com',
'appleorange#msn.edu.com',
'laughable#gmail.com',
'notfunny#pointdexter.com',
'very.latin...word#word.nutherwork.com',
'very.latin..word#word.nutherwork.com',
'my_name_is#orange.org']
Any help would be appreciated!
emails = ['me.you#perp.comp',
'appleorange#msn.edu.cot',
'laughable#gmail.copl',
'notfunny#pointdexter.com',
'very.latin...word#word.nutherwork.com',
'very.latin..word#word.nutherwork.cnm',
'my_name_is#orange.org']
def domain(emails):
for email in emails:
parse_mail = email.split('.')
parse_mail = parse_mail[-1]
if parse_mail[0] == "c":
email = email.replace(parse_mail,"com")
pass
return email
print(domain(emails))
It returns the email without "c" because that's the last one in the array.
Your routine "domain" only returns the last email in the array. If you put the org address higher up, it'll return an email with a "c".
I expect what you're looking for is:
def domain(emails):
for i in range(len(emails)):
parse_mail = emails[i].split('.')
if parse_mail[-1][0] == "c":
parse_mail = emails[i].split('.')[:-1]
parse_mail.append("com")
correct = '.'.join(parse_mail)
emails[i] = correct
pass
return emails
print(domain(emails))
But as Sembei Norimaki, mentioned - this will also auto-correct (erroneously) other extensions beginning with a 'c'.
So basically i bought a book that teaches the basics of python and how to create a random number generator so I decided to go one step further and make a random password generator I found a tutorial online that gave me a good example of why and what is used to make a password generator but i want the output to be saved to a .txt file I do not know what i need to implement to get the result i want this is what i have i'm using python3.
import random
chars = 'abcdefghijklmnopqrstuvwxyz1234567890ABCDEFGHIJKLMNOPQRSTUVWXYZ!, #,#$%^&*.'
number = input('Number of passwords - ')
number = int(number)
length = input('password length? - ')
length = int(length)
answer = input
for P in range(number):
password = ''
for C in range(length):
password += random.choice(chars)
print(password)
password = open("passlist.txt", "a")
password.write(password)
password.close()
file = open('passlist', 'w')
file.write(password)
file.close()
this is what i get in shell
Traceback (most recent call last):
File "C:\User\Desktop\passgen.py", line 21, in <module>
password.write(password)
TypeError: write() argument must be str, not _io.TextIOWrapper
When you open a new file and set it equal to a variable, you are actually creating an _io.TextIOWrapper object. So in this line of code, you are creating this object and storing it in password, getting rid of the password generated in the previous lines of code.
password = open("passlist.txt", "a")
You are then trying to write to the passlist.txt file with this line:
password.write(password)
You are telling password, now an _io.TextIOWrapper object, to write to the passfile.txt the _io.TextIOWrapper object, not the password generated beforehand. This function is expecting a string, and you are now passing an _io.TextIOWrapper object. Since password is no longer a string, that is why you are running into the error.
To fix this, I would suggest creating a new variable:
txtFileWriter = open("passlist.txt", "a")
txtFileWriter.write(password)
txtFileWriter.close()
You may find that after fixing this, only one value is being stored inside your text file. I would recommend properly nesting your for loops:
for P in range(number):
password = ''
for C in range(length):
password += random.choice(chars)
print(password)
The meaning of these for loops can be translated as:
For each password, set the password = ' ' and for each character, add one random character to password.
The problem with this is that you will only have one password after the for loops are complete. You are setting the password value to ' ' each time you run through the outer loop. The only password that will be saved, will be the last value. In order to fix this, I recommend using a list.
I recommend reading through this documentation
I don't want to spoon feed the answers since I realize you are learning python, so I will leave it here. You will want to create a list and then append a value to that list each time you generate a password. After some reading, hopefully this will make sense.
filename = 'passlist.txt'
with open (filename, 'a') as file_object:
file_object.write(password)
Using with will close the file once access is no longer needed.
You also need a list to append your passwords ;)
The error originates from password being re-assigned in password = open("passlist.txt", "a"). This causes and error in the next line as you are attempting to pass password as parameter to itself in password.write(password).
Some farther assistance
You have the right idea but you forgot to indent. All the lines below for P in range(number): should be indented because the program must generate and write a new password until it has satisfied the required amount of passwords.
The password = open("passlist.txt", "a")
password.write(password)
password.close() lines are unnecessary as you are overriding the generated password and assigning that password variable to something that is not a string; that is why you are getting that error.
Here is the code with the adjustments.
import random
chars = 'abcdefghijklmnopqrstuvwxyz1234567890ABCDEFGHIJKLMNOPQRSTUVWXYZ!, #,#$%^&*.'
number = input('Number of passwords - ')
number = int(number)
length = input('password length? - ')
length = int(length)
answer = input
for P in range(number):
password = ''
for C in range(length):
password += random.choice(chars)
print(password)
password += "\n" # writes the password in a new line
file = open('passlist.tx', "a")
file.write(password)
file.close()
I am new learner for python.I am trying to make a basic login accout check, and somehow, my code is not showing what I want. I have defined three user name, and when I run my code, if the first time I put an incorrect user name, the code show account not exit,but it is not shoing. I do not know why
I believe it is my for loop problem, because when I input a wrong account, my i index start at 0 and keep loop until the end index and compare the input username and the exist username in the list. Then after compare all the index if not found user name, then print account not exist, I try to fix this issue, but not find a correct way.
user1=[
{'id':'0001','name':'123','password':'a123', 'balance':0.00},
{'id':'0002','name':'456','password':'a456', 'balance':0.00},
{'id':'0003','name':'789','password':'a789', 'balance':0.00}
]
for x in range(0,4):
name = input('User Name:')
for i in range(len(user1)):
if name == user1[i]['name']:
password = input('Password:')
if password == user1[i]['password']:
print("Success login")
continue
if name != user1[i]['name']:
print("Account not exist, input new one")
If I input wrong user name; it should show account not exist input new one, then I put user name 456 then will ask the correct password.
Look at the logic of your loop body:
for i in range(len(user1)):
if name == user1[i]['name']:
password = input('Password:')
if password == user1[i]['password']:
print("Success login")
continue
if name != user1[i]['name']:
print("Account not exist, input new one")
Regardless of the input, you will never get to the second if statement: any time your program gets to that point, you tell it to continue with the next loop iteration. Try this instead:
for i in range(len(user1)):
if name == user1[i]['name']:
password = input('Password:')
if password == user1[i]['password']:
print("Success login")
else:
print("Account not exist, input new one")
Note that this will work better if you put the all of the accounts into a single dict, so you can access them directly:
user1 = {
'123': {'id':'0001', 'password':'a123', 'balance':0.00},
'456': {'id':'0002', 'password':'a456', 'balance':0.00},
'789': {'id':'0003', 'password':'a789', 'balance':0.00}
}
This allows you to directly access each account by name, rather than searching the entire list for the user trying to log in.
This question already has answers here:
I need to securely store a username and password in Python, what are my options? [closed]
(8 answers)
Closed 5 years ago.
I am trying to create a program that asks the user for, in this example, lets say a username and password, then store this (I assume in a text file). The area I am struggling with is how to allow the user to update this their password stored in the text file? I am writing this in Python.
import getpass
import os
import bcrypt
new=None
def two_hash():
master_key = getpass.getpass('enter pass word ')
salt = bcrypt.gensalt()
combo = salt + master_key
hashed = bcrypt.hashpw(combo , salt)
allow = raw_input('do you want to update pass ')
if allow == 'y':
new = getpass.getpass('enter old pass word ')
combo = salt + new
bcrypt.hashpw(combo , salt)
if ( bcrypt.hashpw(combo , salt) == hashed ):
new = getpass.getpass('enter new pass ')
print new
else :
pass
if __name__ == '__main__':
two_hash()
Note 1 : i wanted to split my code to some function but i can't so help for split it to some function
Because you've asked to focus on how to handle the updates in a text file, I've focused on that part of your question. So, in effect I've focused on answering how would you go about having something that changes in a text file when those changes impact the length and structure of the text file. That question is independent of the thing in the text file being a password.
There are significant concerns related to whether you should store a password, or whether you should store some quantity that can be used to verify a password. All that depends on what you're trying to do, what your security model is, and on what else your program needs to interact with. You've ruled all that out of scope for your question by asking us to focus on the text file update part of the problem.
You might adopt the following pattern to accomplish this task:
At the beginning see if the text file is present. Read it and if so assume you are doing an update rather than a new user
Ask for the username and password. If it is an update prompt with the old values and allow them to be changed
Write out the text file.
Most strategies for updating things stored in text files involve rewriting the text file entirely on every update.
Is this a single user application that you have? If you can provide more information one where you're struggling
You can read the password file (which has usernames and passwords)
- When user authenticate, match the username and password to the combination in text file
- When user wants to change password, then user provides old and new password. The username and old password combination is compared to the one in text file and if matches, stores the new
Try using JSON.
An example of a json file would be this:
{
"Usernames": {
"Username": [
{
"Password": "Password123"
}
]
}
}
Then to edit the json:
jsonloads = json.loads(open('json.json').read()) #Load the json
username = input("Enter your username: ") #Get username as a string
for i in jsonloads["Usernames"]: #Iterate through usernames
if i == username: #If the username is what they entered
passw = input("New password: ") #Ask for new password
jsonloads["Usernames"][i][0]["Password"] = passw #Set the password
jsonFile = open("json.json", "w+") #Open the json
jsonFile.write(json.dumps(jsonloads, indent=4)) #Write
jsonFile.close() #Close it
break #Break out of the for loop
else: #If it remains unbroken
print("You aren't in the database. ")
user = input("Username: ") #Ask for username
passw = input("Password: ") #Ask for password for username
item = {"Password":pass} #Make a dict
jsonloads["Usernames"].update({user: item}) #Add that dict to "Usernames"
with open('json.json','w') as f: #Open the json
f.write(json.dumps(jsonloads, indent=4)) #Write
Something like that should work, haven't tested it though.
Also, remember to always encrypt passwords!