Before we start, please note that I am speaking mostly from the perspective of Swift programming language. However, most, if not all of the below, should be applicable to many other languages.
There are a lot of very useful and easy to use libraries which cover a broad spectrum of functionalities. Also, there are many contributors who invest a lot of effort to make them better and up to date with latest trends. There are also several dependency managers which make them easy to integrate. Some developers do not want to use any libraries and some use them even for small and not complicated projects. Sometimes it is very hard to decide when and whether to use them in your project. There are pros and cons to both approaches.
Based on my experience working on projects that range from not using any (open source) libraries to using many, I may be able to give you some pointers. Before you decide what your approach will be, it is very useful to make an analysis of your project and environment you are working in. I have made a list of things to consider while making such a decision.
1. How to decide
First of all, you should make thorough analysis of your project and answer some questions:
- How big is my project? Will it be actively maintained? This is very important because big projects usually require a lot of maintenance, and using dependencies introduces additional maintenance complexity to the existing effort.
- Do I want to solve some of the core functionality by using some library? If “yes”, it should be the one which is popular and actively maintained. Otherwise, you may end up rewriting a big chunk of your project when it becomes outdated and stops working.
- Do I need some libraries for specific purposes, eg. for animations, progress indication, networking? Does my client want to include some closed source libraries to the project? If you answered any of these questions with a “yes”, you should limit the number of dependencies you use, as more dependencies sometimes mean more problems.
- How much time do I have for implementation? If there is a time limit and you need to do it quickly, for sure it is better to choose an existing library.
- How many developers will work on the project? Will more developers be involved in the future? If more developers will be working on a project, you should be careful when including complex libraries which are not part of the standard in your working environment. Developers who might be inexperienced or did not deal with these libraries will take additional time learning to use them. One good example is a library for reactive programming - RxSwift. Such a library, which changes the approach of implementation, will certainly require more time by developers who have never used it. If time is of essence, and you cannot accommodate this additional learning time into the timeline for the project, consider sticking to standards or some libraries which are familiar to everyone in the team.
- Could I develop my own solution, for some feature, in reasonable time? If you decide to go this way, you can help yourself and speed up the process by extracting some parts of the existing libraries for only the functionalities you need.
Will there be anyone available to maintain your own solution? You should always keep in mind that you will need to have resources for its maintenance.
Once you have the answers to the questions above, you should have a decent idea in which direction to go.
2. Using third party libraries
If you decide to use third-party libraries, the first steps you should do are:
- Search the web to find recommendations for commonly used libraries.
- If you have multiple projects, try to use the same libraries in them. This will flatten the learning curve and make the onboarding process for new developers easier.
- Try to generalise the usage of more complex libraries across the projects by writing a wrapper. This way they will be used in the same manner everywhere.
Once you find the libraries you would like to use, you also need to consider following questions:
- Which dependency manager to use? There are pros and cons to each of them. Investigate which one is best for your needs. I would not recommend having several different dependency managers as most of the popular libraries have support for all of them anyway, so just stick to one.
- How many contributors and stars does the library have? How many bugs and issues has it reported? More contributors and good feedback increases the chances that the bugs will be fixed in reasonable time and the library will continue to be actively maintained.
- When was the library last updated? If it was updated many years ago, there is a high chance it was written in an unsupported version, or does not have support for the latest version of the programming language of your choice. This is especially true for languages like Swift.
- How many functionalities does the library have and do I need all of them? Usually, simple is better. This is why you probably do not want to integrate some big library with many unnecessary functionalities to do just the one thing you need.
- How easily can the library be integrated into my code? If it is hard, reconsider looking into some similar solution which is easier to integrate.
- Is the library well documented? If the documentation is not good and you have to spend more time discovering how to use the library than it would take you to implement functionality by yourself, then it is obviously not a good choice.
Once you decided to add a specific third party library to your project, it is good to do the following:
- No matter if you use one or more libraries, I would recommend documenting the list along with a short description of what they are used for in a single place. From my experience it is not very encouraging when you open a new project and see a lot of libraries which you are not familiar with and have to spend time to find what they are used for.
- Make your own documentation with a short description of how the library is used and in a which way. This is especially useful for some more complex libraries which developers could use in different ways.This way you can try to enforce consistency in usage both on the same and other projects.
- Once you have the library in your project, regularly check if it is up to date. If possible keep it updated, otherwise if it is no longer maintained, consider replacing it with a new one by following all appropriate steps above. The sooner you do it the less problems you will have in the future.
- Sometimes the new version of Swift comes with new functionalities which can completely replace libraries you use. When this happens consider switching to the Swift implementation and getting rid of dependency. Good example is Codable protocol which simplifies conversion of Swift objects to JSON and other ways around, and there is no need to use third party libraries for it.
3. Not using third-party libraries
Advantages of this approach are that you do not depend on other people from the open source community and you can always have your code up to date and bugs resolved in a timely manner. Although you decided not to use any of third-party libraries, you should still have proper planning and analysis for your project:
- You need to make a detailed plan of your resources and time. Even when there is a lot of boilerplate code, it still requires certain time for implementation. Good example is implementation of API client which almost every project needs, but it still takes time to add it.
- Although you are implementing everything in-house, you will still have reusable code and functionalities, so it is good to have them as libraries in order to reuse them and save time in the future. Decide which dependency manager you will use for maintaining your internal libraries.
- Find time to make detailed documentation of your own libraries. The documentation on how to use them is very important and saves a lot of developer’s time.
- Use extensions in order to add new functionalities to the existing classes, structures, enumerations or protocols.
Through the questions and steps above I tried to give some overview and feeling about what it means to use or not use third-party libraries in iOS (with focus on programming in Swift). It turns out there are more steps to go through if you decide to use libraries, but more steps does not necessarily mean more time spent implementing something. It is important to keep in mind that every functionality that is not core of your project and is easily replaceable can be included to your project as dependency, as it should not affect your project in a major way.
Some examples are some helper libraries (library for downloading and caching images, saving data to keychain, auto layout helpers etc..), progress indicator, animations as they will not require a lot of developer time to be implemented.
One of the big benefits of not using libraries is learning. For junior developers who have to do some of it, it is more beneficial not to use the libraries, because by doing things by themselves they learn more. If you start with a third-party network client as a junior developer there is a high chance you will never truly learn about session and network requests and exactly how they work.
My final conclusion is: while you can live without libraries, it does not mean you should. Detailed planning and analysis of your project, needs, resources and time are the key factors in helping you decide which approach to take.