Projects STRLCPY Osintgram Commits 80361acc
🤬
Revision indexing in progress... (symbol navigation in revisions will be accurate after indexed)
  • ■ ■ ■ ■ ■ ■
    Osintgram.py
    skipped 16 lines
    17 17   geolocator = Nominatim()
    18 18   user_id = None
    19 19   target = ""
     20 + writeFile = False
    20 21   
    21 22   def __init__(self, target):
    22 23   self.target = target
    skipped 59 lines
    82 83   sort_addresses = sorted(address.items(), key=lambda p: p[1], reverse=True) #sorting
    83 84   
    84 85   return sort_addresses
     86 + 
     87 + def setWriteFile(self, bool):
     88 + if(bool):
     89 + pc.printout("Write to file: ")
     90 + pc.printout("enabled", pc.GREEN)
     91 + pc.printout("\n")
     92 + else:
     93 + pc.printout("Write to file: ")
     94 + pc.printout("disabled", pc.RED)
     95 + pc.printout("\n")
     96 + 
     97 + self.writeFile = bool
    85 98   
    86 99   
    87 100   def __getUserFollowigs__(self, id):
    skipped 78 lines
    166 179   
    167 180   sortE = sorted(hashtag_counter.items(), key=lambda value: value[1], reverse=True)
    168 181   
     182 + if(self.writeFile):
     183 + file_name = "output/" + self.target + "_hashtags.txt"
     184 + file = open(file_name, "w")
     185 + for k,v in sortE:
     186 + file.write(str(v) + ". " + str(k.decode('utf-8'))+"\n")
     187 + file.close()
     188 +
     189 + 
    169 190   for k,v in sortE:
    170 191   print( str(v) + ". " + str(k.decode('utf-8')))
     192 +
     193 + 
    171 194   
    172 195   def getTotalLikes(self, id):
    173 196   pc.printout("Searching for target total likes...\n")
    skipped 21 lines
    195 218   
    196 219   if not 'next_max_id' in only_id:
    197 220   break
     221 + 
     222 + if(self.writeFile):
     223 + file_name = "output/" + self.target + "_likes.txt"
     224 + file = open(file_name, "w")
     225 + file.write(str(like_counter) + " likes in " + str(counter) + " posts\n")
     226 + file.close()
     227 + 
    198 228   pc.printout(str(like_counter), pc.MAGENTA)
    199 229   pc.printout(" likes in " + str(counter) + " posts\n")
    200 230  
    skipped 23 lines
    224 254   
    225 255   if not 'next_max_id' in only_id:
    226 256   break
     257 + 
     258 + if(self.writeFile):
     259 + file_name = "output/" + self.target + "_comments.txt"
     260 + file = open(file_name, "w")
     261 + file.write(str(comment_counter) + " comments in " + str(counter) + " posts\n")
     262 + file.close()
     263 + 
    227 264   pc.printout(str(comment_counter), pc.MAGENTA)
    228 265   pc.printout(" comments in " + str(counter) + " posts\n")
    229 266   
    skipped 52 lines
    282 319   for i in range(len(ids)):
    283 320   t.add_row([post[i], full_name[i], username[i], str(ids[i])])
    284 321   
     322 + if(self.writeFile):
     323 + file_name = "output/" + self.target + "_tagged.txt"
     324 + file = open(file_name, "w")
     325 + file.write(str(t))
     326 + file.close()
     327 + 
    285 328   print(t)
    286 329   else:
    287 330   pc.printout("Sorry! No results found :-(\n", pc.RED)
    skipped 15 lines
    303 346   for address, time in addrs:
    304 347   t.add_row([str(i), address, time])
    305 348   i = i + 1
     349 + 
     350 + if(self.writeFile):
     351 + file_name = "output/" + self.target + "_addrs.txt"
     352 + file = open(file_name, "w")
     353 + file.write(str(t))
     354 + file.close()
     355 + 
    306 356   print(t)
    307 357   
    308 358   def getFollowers(self, id):
    skipped 7 lines
    316 366  
    317 367   for i in followers:
    318 368   t.add_row([str(i['pk']), i['username'], i['full_name']])
     369 + 
     370 + if(self.writeFile):
     371 + file_name = "output/" + self.target + "_followers.txt"
     372 + file = open(file_name, "w")
     373 + file.write(str(t))
     374 + file.close()
     375 + 
    319 376   print(t)
    320 377   
    321 378   def getFollowings(self, id):
    skipped 7 lines
    329 386   
    330 387   for i in followings:
    331 388   t.add_row([str(i['pk']), i['username'], i['full_name']])
     389 + 
     390 + if(self.writeFile):
     391 + file_name = "output/" + self.target + "_followings.txt"
     392 + file = open(file_name, "w")
     393 + file.write(str(t))
     394 + file.close()
     395 + 
    332 396   print(t)
    333 397   
    334 398   def getUserID(self, username):
    skipped 5 lines
    340 404   sys.exit(2)
    341 405   
    342 406   data = json.load(content)
     407 + 
     408 + if(self.writeFile):
     409 + file_name = "output/" + self.target + "_user_id.txt"
     410 + file = open(file_name, "w")
     411 + file.write(str(data['graphql']['user']['id']))
     412 + file.close()
    343 413   return data['graphql']['user']['id']
    344 414   
    345 415   def getUserInfo(self):
    skipped 44 lines
    390 460   node = i.get('node')
    391 461   t.add_row([str(count), node.get('accessibility_caption')])
    392 462   count += 1
     463 + 
     464 + if(self.writeFile):
     465 + file_name = "output/" + self.target + "_photodes.txt"
     466 + file = open(file_name, "w")
     467 + file.write(str(t))
     468 + file.close()
     469 + 
     470 +
    393 471   print(t)
    394 472   else:
    395 473   pc.printout("Sorry! No results found :-(\n", pc.RED)
     474 + 
     475 + 
     476 + def getUserPhoto(self, id):
     477 + limit = -1
     478 + pc.printout("How many photos you want to download (default all): ", pc.YELLOW)
     479 + l = input()
     480 + try:
     481 + if l == "":
     482 + pc.printout("Downloading all photos avaible...\n")
     483 + else:
     484 + limit = int(l)
     485 + pc.printout("Downloading " + l + " photos...\n")
     486 + 
     487 + except ValueError:
     488 + pc.printout("Wrong value entered\n", pc.RED)
     489 + return
     490 + 
     491 +
     492 + a = None #helper
     493 + counter = 0
     494 + while True:
     495 + if (a == None):
     496 + self.api.getUserFeed(id)
     497 + a = self.api.LastJson['items']#photos 00, 01, 02...
     498 + only_id = self.api.LastJson #all LastJson with max_id param
     499 +
     500 + else:
     501 + self.api.getUserFeed(id, only_id['next_max_id']) #passing parameter max_id
     502 + only_id = self.api.LastJson
     503 + a = self.api.LastJson['items']
     504 + 
     505 + try:
     506 + for item in a:
     507 + if counter == limit:
     508 + break
     509 + if "image_versions2" in item:
     510 + counter = counter + 1
     511 + url = item["image_versions2"]["candidates"][0]["url"]
     512 + photo_id = item["id"]
     513 + end = "output/" + self.target + "_" + photo_id + ".jpg"
     514 + urllib.request.urlretrieve(url, end)
     515 + sys.stdout.write("\rDownloaded %i" % counter)
     516 + sys.stdout.flush()
     517 + else:
     518 + carousel = item["carousel_media"]
     519 + for i in carousel:
     520 + if counter == limit:
     521 + break
     522 + counter = counter + 1
     523 + url = i["image_versions2"]["candidates"][0]["url"]
     524 + photo_id = i["id"]
     525 + end = "output/" + self.target + "_" + photo_id + ".jpg"
     526 + urllib.request.urlretrieve(url, end)
     527 + sys.stdout.write("\rDownloaded %i" % counter)
     528 + sys.stdout.flush()
     529 + 
     530 + except AttributeError:
     531 + pass
     532 +
     533 + except KeyError:
     534 + pass
     535 + 
     536 + if not 'next_max_id' in only_id:
     537 + break
     538 +
     539 + sys.stdout.write(" photos")
     540 + sys.stdout.flush()
     541 + 
     542 + pc.printout("\nWoohoo! We downloaded " + str(counter) + " photos (saved in output/ folder) \n", pc.GREEN)
     543 + 
     544 + 
     545 + def getCaptions(self, id):
     546 + pc.printout("Searching for target captions...\n")
     547 +
     548 + a = None #helper
     549 + counter = 0
     550 + captions = []
     551 + while True:
     552 + if (a == None):
     553 + self.api.getUserFeed(id)
     554 + a = self.api.LastJson['items']#photos 00, 01, 02...
     555 + only_id = self.api.LastJson #all LastJson with max_id param
     556 +
     557 + else:
     558 + self.api.getUserFeed(id, only_id['next_max_id']) #passing parameter max_id
     559 + only_id = self.api.LastJson
     560 + a = self.api.LastJson['items']
     561 + 
     562 + try:
     563 + for item in a:
     564 + if "caption" in item:
     565 + if item["caption"] != None:
     566 + text = item["caption"]["text"]
     567 + captions.append(text)
     568 + counter = counter + 1
     569 + sys.stdout.write("\rFound %i" % counter)
     570 + sys.stdout.flush()
     571 + 
     572 + except AttributeError:
     573 + pass
     574 +
     575 + except KeyError:
     576 + pass
     577 + 
     578 + if not 'next_max_id' in only_id:
     579 + break
     580 +
     581 + sys.stdout.write(" captions")
     582 + sys.stdout.flush()
     583 + 
     584 + if counter > 0:
     585 + pc.printout("\nWoohoo! We found " + str(counter) + " captions\n", pc.GREEN)
     586 + 
     587 +
     588 + 
     589 + if(self.writeFile):
     590 + file_name = "output/" + self.target + "_captions.txt"
     591 + file = open(file_name, "w")
     592 + for s in captions:
     593 + file.write(s + "\n")
     594 + file.close()
     595 + 
     596 + for s in captions:
     597 + print(s + "\n")
     598 + 
     599 + else:
     600 + pc.printout("Sorry! No results found :-(\n", pc.RED)
     601 +
     602 + return
     603 + 
     604 + 
     605 + def getMediaType(self, id):
     606 + pc.printout("Searching for target captions...\n")
     607 +
     608 + a = None #helper
     609 + counter = 0
     610 + photo_counter = 0
     611 + video_counter = 0
     612 +
     613 + while True:
     614 + if (a == None):
     615 + self.api.getUserFeed(id)
     616 + a = self.api.LastJson['items']#photos 00, 01, 02...
     617 + only_id = self.api.LastJson #all LastJson with max_id param
     618 +
     619 + else:
     620 + self.api.getUserFeed(id, only_id['next_max_id']) #passing parameter max_id
     621 + only_id = self.api.LastJson
     622 + a = self.api.LastJson['items']
     623 + 
     624 + try:
     625 + for item in a:
     626 + if "media_type" in item:
     627 + if item["media_type"] == 1:
     628 + photo_counter = photo_counter + 1
     629 + elif item["media_type"] == 2:
     630 + video_counter = video_counter + 1
     631 + 
     632 + counter = counter + 1
     633 + sys.stdout.write("\rChecked %i" % counter)
     634 + sys.stdout.flush()
     635 + 
     636 + except AttributeError:
     637 + pass
     638 +
     639 + except KeyError:
     640 + pass
     641 + 
     642 + if not 'next_max_id' in only_id:
     643 + break
     644 +
     645 + sys.stdout.write(" posts")
     646 + sys.stdout.flush()
     647 + 
     648 + if counter > 0:
     649 + 
     650 + if(self.writeFile):
     651 + file_name = "output/" + self.target + "_mediatype.txt"
     652 + file = open(file_name, "w")
     653 + file.write(str(photo_counter) + " photos and " + str(video_counter) \
     654 + + " video posted by target\n")
     655 + file.close()
     656 + 
     657 + 
     658 + pc.printout("\nWoohoo! We found " + str(photo_counter) + " photos and " + str(video_counter) \
     659 + + " video posted by target\n", pc.GREEN)
     660 + 
     661 + else:
     662 + pc.printout("Sorry! No results found :-(\n", pc.RED)
     663 +
     664 + return
     665 + 
     666 +
     667 +
     668 + def getUserPropic(self):
     669 + try:
     670 + content = urllib.request.urlopen("https://www.instagram.com/" + str(self.target) + "/?__a=1" )
     671 + except urllib.error.HTTPError as err:
     672 + if(err.code == 404):
     673 + print("Oops... " + str(self.target) + " non exist, please enter a valid username.")
     674 + sys.exit(2)
     675 + 
     676 + data = json.load(content)
     677 + 
     678 + URL = ""
     679 + 
     680 + uurl = data["graphql"]["user"]
     681 + if "profile_pic_url_hd" in uurl:
     682 + URL = data["graphql"]["user"]["profile_pic_url_hd"]
     683 + else:
     684 + URL = data["graphql"]["user"]["profile_pic_url"]
     685 + 
     686 + if URL != "":
     687 + end = "output/" + self.target + "_propic.jpg"
     688 + urllib.request.urlretrieve(URL, end)
     689 + pc.printout("Target propic saved in output folder\n", pc.GREEN)
     690 + 
     691 + else:
     692 + pc.printout("Sorry! No results found :-(\n", pc.RED)
     693 + 
     694 + 
     695 + 
     696 +
     697 + 
     698 + 
    396 699   
    397 700   
    398 701   
    skipped 22 lines
  • ■ ■ ■ ■ ■
    README.md
     1 +[![](https://img.shields.io/badge/version-0.3-green)](https://img.shields.io/badge/version-0.3-green)
     2 +[![](https://img.shields.io/badge/license-GPLv3-blue)](https://img.shields.io/badge/license-GPLv3-blue)
     3 + 
     4 + 
    1 5  # Osintgram
    2 6  Osintgram is a tool for **OSINT** on Instagram.
    3  -OSINT is a fork of https://github.com/LevPasha/Instagram-API-python and https://github.com/woj-ciech/OSINT/tree/master/insta.
     7 +Osintgram is a fork of https://github.com/LevPasha/Instagram-API-python and https://github.com/woj-ciech/OSINT/tree/master/insta.
    4 8   
    5 9  **I don't assume any responsability for the use of this tool**
    6 10   
     11 +Osintgram offers an interactive shell to perform analysis on Instagram account of any users by its nickname. You can get:
     12 +```
     13 +- info Get target info
     14 +- addrs Get all registered addressed by target photos
     15 +- followers Get target followers
     16 +- followings Get users followed by target
     17 +- hashtags Get hashtags used by target
     18 +- likes Get total likes of target's posts
     19 +- comments Get total comments of target's posts
     20 +- tagged Get list of users tagged by target
     21 +- photodes Get description of target's photos
     22 +- photos Download user's photos in output folder
     23 +- captions Get user's photos captions
     24 +- mediatype Get user's posts type (photo or video)
     25 +- propic Download user's profile picture
     26 + 
     27 +```
     28 +You can find detailed commands usage [here](commands.md).
     29 + 
     30 + 
     31 +The tools use Python3.
     32 + 
     33 +## Changelog
     34 +- v0.1 initial release
     35 +- v0.2 added feature to write in file the output of commands
     36 +- v0.3 added features: photos, captions, mediatype, propic
     37 + 
    7 38  ## Tools
    8  -![Imgur](https://imgur.com/RJ1JplI.jpg)
     39 +![](cmd.png)
    9 40   
    10 41  ## Installation
    11 42  1. Fork/Clone/Download this repo
    skipped 5 lines
    17 48   
    18 49   `cd Osintgram`
    19 50   
     51 +3. Run `pip3 install -r requirements.txt`
    20 52   
    21  -3. Create a subdirectory `config`
     53 + 
     54 +4. Create a subdirectory `config`
    22 55   
    23 56   `mkdir config`
    24 57   
    25  -4. Create in `config` folder the file: `username.conf` and write your Instagram account username
     58 +5. Create in `config` folder the file: `username.conf` and write your Instagram account username
    26 59   
    27  -5. Create in `config` folder the file: `pw.conf` and write your Instagram account password
     60 +6. Create in `config` folder the file: `pw.conf` and write your Instagram account password
    28 61   
    29  -6. Run the main.py script
     62 +7. Run the main.py script
    30 63   
    31  - `python main.py <target username>`
     64 + `python3 main.py <target username>`
     65 + 
     66 +## Updating
     67 + 
     68 +Run `git pull` in Osintgram directory
    32 69   
  • cmd.png
  • ■ ■ ■ ■ ■ ■
    commands.md
     1 +# Commands list and usage
     2 +```
     3 +- info Get target info
     4 +- addrs Get all registered addressed by target photos
     5 +- followers Get target followers
     6 +- followings Get users followed by target
     7 +- hashtags Get hashtags used by target
     8 +- likes Get total likes of target's posts
     9 +- comments Get total comments of target's posts
     10 +- tagged Get list of users tagged by target
     11 +- photodes Get description of target's photos
     12 +- photos Download user's photos in output folder
     13 +- captions Get user's photos captions
     14 +- mediatype Get user's posts type (photo or video)
     15 +- propic Download user's profile picture
     16 + 
     17 +```
     18 + 
     19 +### list (or help)
     20 +Show all commands avaible.
     21 + 
     22 +### exit
     23 +Exit from Osintgram
     24 + 
     25 +### FILE
     26 +Can set preference to save commands output in output folder. It save output in `<target username>_<command>.txt` file.
     27 +With `FILE=y` you can enable saving in file.
     28 +With `FILE=y` you can disable saving in file.
     29 + 
     30 +### info
     31 +Show target info like:
     32 +- id
     33 +- full name
     34 +- biography
     35 +- followed
     36 +- follow
     37 +- is business account?
     38 +- business catagory (if target has business account)
     39 +- is verified?
     40 + 
     41 +### addrs
     42 +Return a list with address (GPS) tagged by target in his photos.
     43 +The list has post, address and date fields.
     44 + 
     45 +### followers
     46 +Return a list with target followers with id, nickname and full name
     47 + 
     48 +### followings
     49 +Return a list with users followed by target with id, nickname and full name
     50 + 
     51 +### hashtags
     52 +Return a list with all hashtag used by target in his photos
     53 + 
     54 +### likes
     55 +Return the total number of likes in target's posts
     56 + 
     57 +### comments
     58 +Return the total number of comments in target's posts
     59 + 
     60 +### photodes
     61 +Return a list with the description of the content of target's photos
     62 + 
     63 +### photos
     64 +Download all target's photos in output folder.
     65 +When you run the command, script ask you how many photos you want to download.
     66 +Type ENTER to download all photos avaible or type a number to choose how many photos you want download.
     67 +```
     68 +Run a command: photos
     69 +How many photos you want to download (default all):
     70 +```
     71 + 
     72 +### captions
     73 +Return a list of all captions used by target in his photos.
     74 + 
     75 +### mediatype
     76 +Return the number of photos and video shared by target
     77 + 
     78 +### propic
     79 +Download target profile picture (HD if is avaible)
     80 + 
     81 + 
     82 + 
     83 + 
     84 + 
     85 + 
  • ■ ■ ■ ■ ■
    main.py
    skipped 13 lines
    14 14   pc.printout("\_______ /____ >__|___| /__| \___ /|__| (____ /__|_| /\n", pc.YELLOW)
    15 15   pc.printout(" \/ \/ \/ /_____/ \/ \/ \n", pc.YELLOW)
    16 16   print('\n')
    17  - pc.printout("Version 0.1 - Developed by Giuseppe Criscione - 2019\n\n", pc.YELLOW)
     17 + pc.printout("Version 0.3 - Developed by Giuseppe Criscione - 2019\n\n", pc.YELLOW)
    18 18   pc.printout("Type 'list' to show all allowed commands\n")
     19 + pc.printout("Type 'FILE=y' to save results to files like '<target username>_<command>.txt (deafult is disabled)'\n")
     20 + pc.printout("Type 'FILE=n' to disable saving to files'\n")
    19 21   
    20 22  
    21 23   
     24 + 
     25 + 
    22 26  def cmdlist():
    23 27   #print("set <username>\t Set user to analize")
    24 28   #print("clear\t\t Remove the user setted")
     29 + pc.printout("FILE=y/n\t")
     30 + print("Enable/disable output in a '<target username>_<command>.txt' file'")
    25 31   pc.printout("info\t\t")
    26 32   print("Get target info")
    27 33   pc.printout("addrs\t\t")
    skipped 12 lines
    40 46   print("Get list of users tagged by target")
    41 47   pc.printout("photodes\t")
    42 48   print("Get description of target's photos")
     49 + pc.printout("photos\t\t")
     50 + print("Download target's photos in output folder")
     51 + pc.printout("captions\t")
     52 + print("Get target's photos captions")
     53 + pc.printout("mediatype\t")
     54 + print("Get target's posts type (photo or video)")
     55 + pc.printout("propic\t\t")
     56 + print("Download target's profile picture")
    43 57   
    44 58   
    45 59  printlogo()
    skipped 14 lines
    60 74   if(cmd == "quit" or cmd == "exit"):
    61 75   pc.printout("Goodbye!\n", pc.RED)
    62 76   sys.exit(0)
    63  - elif cmd == "list":
     77 + elif cmd == "list" or cmd=="help":
    64 78   cmdlist()
    65 79   elif cmd == "addrs":
    66 80   api.getAddrs(id)
    skipped 13 lines
    80 94   api.getPeopleTaggedByUser(id)
    81 95   elif cmd == "photodes":
    82 96   api.getPhotoDescription()
    83  -
     97 + elif cmd == "FILE=y":
     98 + api.setWriteFile(True)
     99 + elif cmd == "FILE=n":
     100 + api.setWriteFile(False)
     101 + elif cmd == "photos":
     102 + api.getUserPhoto(id)
     103 + elif cmd == "captions":
     104 + api.getCaptions(id)
     105 + elif cmd == "mediatype":
     106 + api.getMediaType(id)
     107 + elif cmd == "propic":
     108 + api.getUserPropic()
    84 109  
    85 110   else:
    86 111   pc.printout("Unknown command\n", pc.RED)
    skipped 3 lines
  • ■ ■ ■ ■ ■
    output/dont_delete_this_folder.txt
     1 +Please don't deleate this folder.
  • ■ ■ ■ ■
    requirements.txt
    1 1  requests==2.20.0
    2  -requests-toolbelt==2.1.0
     2 +requests-toolbelt==0.9.1
    3 3  moviepy==0.2.2.11
    4 4  geopy==1.11
    5 5  prettytable==0.7.2
Please wait...
Page is in error, reload to recover